How to make the Layout change when an item changes
-
Hi,
when i change the size of an Item i would like the other to move, like if the new height (int the example) was the same at the begining. When i do this code it doesn't work. Here is a peace of code to illustrate thisimport QtQuick 2.2
import QtQuick.Layouts 1.1
import QtQuick.Controls 1.1ApplicationWindow {
minimumHeight: 100
maximumHeight: 300
minimumWidth: 100
maximumWidth: 300
width: 300
height: 300ColumnLayout { id: layoutC anchors.fill: parent // Doesn't work with that //width: 100 // Works with that onWidthChanged: console.log("Column Width : "+width) Rectangle { id: rect1 color: "red" visible: true onWidthChanged: console.log("Rectangle 1 Width : "+width) Layout.fillHeight: true // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 Layout.maximumHeight: 100 } Rectangle { id: rect2 color: "#028000" //width: rectangle.width height: 200 onWidthChanged: console.log("Rectangle 2 Width : "+width) Layout.fillHeight: false // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 Layout.maximumHeight: 300 MouseArea { anchors.fill: parent onClicked: { if (rect2.height==100) { rect2.height=200 rect3.height-=100 // Not Good i Know it is to illustrate : Remove it } else { rect2.height=100 rect3.height+=100 // Not Good i Know it is to illustrate : Remove it } console.log("clicked") } } } Rectangle { id: rect3 color: "#0500ff" onWidthChanged: console.log("Rectangle 3 Width : "+width) onHeightChanged: console.log("Rectangle 3 Height : "+height) Layout.fillHeight: true // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 anchors.top: rect2.bottom // Remove it and you will see that } }
}
What i want is that it works the same as if the line when i put "Remove" was not there.
Thanks
Sincerely -
Hi,
when i change the size of an Item i would like the other to move, like if the new height (int the example) was the same at the begining. When i do this code it doesn't work. Here is a peace of code to illustrate thisimport QtQuick 2.2
import QtQuick.Layouts 1.1
import QtQuick.Controls 1.1ApplicationWindow {
minimumHeight: 100
maximumHeight: 300
minimumWidth: 100
maximumWidth: 300
width: 300
height: 300ColumnLayout { id: layoutC anchors.fill: parent // Doesn't work with that //width: 100 // Works with that onWidthChanged: console.log("Column Width : "+width) Rectangle { id: rect1 color: "red" visible: true onWidthChanged: console.log("Rectangle 1 Width : "+width) Layout.fillHeight: true // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 Layout.maximumHeight: 100 } Rectangle { id: rect2 color: "#028000" //width: rectangle.width height: 200 onWidthChanged: console.log("Rectangle 2 Width : "+width) Layout.fillHeight: false // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 Layout.maximumHeight: 300 MouseArea { anchors.fill: parent onClicked: { if (rect2.height==100) { rect2.height=200 rect3.height-=100 // Not Good i Know it is to illustrate : Remove it } else { rect2.height=100 rect3.height+=100 // Not Good i Know it is to illustrate : Remove it } console.log("clicked") } } } Rectangle { id: rect3 color: "#0500ff" onWidthChanged: console.log("Rectangle 3 Width : "+width) onHeightChanged: console.log("Rectangle 3 Height : "+height) Layout.fillHeight: true // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 anchors.top: rect2.bottom // Remove it and you will see that } }
}
What i want is that it works the same as if the line when i put "Remove" was not there.
Thanks
Sincerely@archqt
Frankly, I haven't understood what you're trying to achieve. You have three rectangles: "red", "green" and "blue" inside an ApplicationWindow that is resizable to some extent, but generally size-constrained. It can only become smaller, not larger than with what it starts. Questions about your intentions:- top rectangle "red" is always to stay at constant height?
- width of rectangles is not the problem here, right? They always fill the entire window width. I suppose this is what you want?
- when you shrink the window vertically, neither middle rectangle "green" shrinks nor bottom rectangle "blue" moves upwards. Instead, "green" stays at constant height and "blue" eventually vanishes below window border. Is this what you wanted or do you want "green" to shrink and "blue" to keep its height when the window is shrunk?
- when you click inside "green", "green"'s height is reduced and "blue" grows. Do you want "blue" to be of constant height all times instead? Or do you want "blue" to keep its height and create a blank area below it?
- when I remove the last line and click inside "green", "green" shrinks, "blue" keeps size and position and a gap between "green" and "blue" is created. This is likely not what you want? (Otherwise you could just have left out that line already?)
So, do you want a gap / blank area somewhere (below or above "blue") if "green" is shrunk, or do you want the new free space filled with something else? Or do my descriptions not match your experience when executing your piece of QML?
-
Hi,
this is an example to explain my problem. What i want is quite simple : when i change the "green rectangle" height i want that the "blue rectangle" takes the place automaticaly. It seems that the Layout calculates the size (in my example the height only) at the creation and that when an item changes its size the calculation is not done anymore. I want the calculation done everytime an item cahnges its size.
In the example i only changes the height.Of course if i change the size of the window i want the size of the items to change.
This is for me the behaviour of a layout. Is there a way to change that ? Thanks
Sincerely -
Hi,
this is an example to explain my problem. What i want is quite simple : when i change the "green rectangle" height i want that the "blue rectangle" takes the place automaticaly. It seems that the Layout calculates the size (in my example the height only) at the creation and that when an item changes its size the calculation is not done anymore. I want the calculation done everytime an item cahnges its size.
In the example i only changes the height.Of course if i change the size of the window i want the size of the items to change.
This is for me the behaviour of a layout. Is there a way to change that ? Thanks
Sincerely@archqt said:
this is an example to explain my problem. What i want is quite simple : when i change the "green rectangle" height i want that the "blue rectangle" takes the place automaticaly.
I'm sorry, but this is exactly what already happens here, using your original code snipplet, when I click inside "green": "blue" grows upwards to fill the additional space. Doesn't the same happen on your installation?
It seems that the Layout calculates the size (in my example the height only) at the creation and that when an item changes its size the calculation is not done anymore. I want the calculation done everytime an item cahnges its size.
You should keep in mind that a layout manager is typically responsible for managing both positions and dimensions of its client items. It will do this continuously if you let it and don't interfere. If you want to change sizes of items manually / forcefully override them, then working with some anchors only may be a better option?
-
@archqt said:
this is an example to explain my problem. What i want is quite simple : when i change the "green rectangle" height i want that the "blue rectangle" takes the place automaticaly.
I'm sorry, but this is exactly what already happens here, using your original code snipplet, when I click inside "green": "blue" grows upwards to fill the additional space. Doesn't the same happen on your installation?
It seems that the Layout calculates the size (in my example the height only) at the creation and that when an item changes its size the calculation is not done anymore. I want the calculation done everytime an item cahnges its size.
You should keep in mind that a layout manager is typically responsible for managing both positions and dimensions of its client items. It will do this continuously if you let it and don't interfere. If you want to change sizes of items manually / forcefully override them, then working with some anchors only may be a better option?
Hi,
sure it works because i use an anchor (remove it). But as everything is in a layout when an item has it size that changes it should say to the Layout that size changed so the Layout can recalculate it.
In my real project what i have done is this : i have 3 éléments and the second element can be hidden or not (depends if the user wanna see the values in it). The third element draws line, square...depending of the data in the second element.
What i did is that i use Layout to manage size, and i use only visible property for the second element.
So when second element is hidden the third element takes all the size (good news). But for a better design approch i decided to modify the size of the second elements (and with a behavior i do a dynamic animation) instead of using the visible property and....it doesn't work at all the third element doesn't change its size.
So my real answer is : Why when i change visible (false/true) to the second element it works but when i modify only the height of it, it doesn't work ?
Thanks
Sincerely -
Hi again,
strange, when i click in the green rectangle it changes it size but when i resize the window the size came back to the original size ? why ?
Sincerelyimport QtQuick 2.2
import QtQuick.Layouts 1.1
import QtQuick.Controls 1.1ApplicationWindow {
width: layoutC.implicitWidth
height: layoutC.implicitHeightColumnLayout { id: layoutC anchors.fill: parent Rectangle { id: rect1 color: "red" visible: true onWidthChanged: console.log("Rectangle 1 Width : "+width) Layout.fillHeight: false // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 Layout.maximumHeight: 100 } Rectangle { id: rect2 color: "#028000" //width: rectangle.width height: 150 onHeightChanged: console.log("Rectangle 2 Height : "+height) Layout.fillHeight: false // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 Layout.maximumHeight: 300 MouseArea { anchors.fill: parent onClicked: { if (rect2.height==100) { rect2.height=200 //rect3.height-=100 // Not Good i Know it is to illustrate : Remove it } else { rect2.height=100 //rect3.height+=100 // Not Good i Know it is to illustrate : Remove it } console.log("clicked") } } } Rectangle { id: rect3 color: "#0500ff" onHeightChanged: console.log("Rectangle 3 Height : "+height) Layout.fillHeight: true // Doesn't extend Layout.fillWidth: true // Doesn't extend Layout.minimumHeight: 50 //anchors.top: rect2.bottom // Remove it and you will see that } }
}
-
Hi,
sure it works because i use an anchor (remove it). But as everything is in a layout when an item has it size that changes it should say to the Layout that size changed so the Layout can recalculate it.
In my real project what i have done is this : i have 3 éléments and the second element can be hidden or not (depends if the user wanna see the values in it). The third element draws line, square...depending of the data in the second element.
What i did is that i use Layout to manage size, and i use only visible property for the second element.
So when second element is hidden the third element takes all the size (good news). But for a better design approch i decided to modify the size of the second elements (and with a behavior i do a dynamic animation) instead of using the visible property and....it doesn't work at all the third element doesn't change its size.
So my real answer is : Why when i change visible (false/true) to the second element it works but when i modify only the height of it, it doesn't work ?
Thanks
Sincerely@archqt
How about this approach then? (Simplified!) When you resize the window, "red" and "green" keep their constant height, while "blue" fills all remaining bottom space. However, the size of "green" can be changed forcefully. Here, by clicking into it.ApplicationWindow { width: 300; height: 300 Column { anchors.fill: parent Rectangle { width: parent.width color: "red" height: 50 } Rectangle { id: green color: "green" height: 50 width: parent.width MouseArea { anchors.fill: parent onClicked: green.height ^= 128 } } Rectangle { color: "blue" width: parent.width height: parent.height - y } } }
Note that this approach doesn't use ColumnLayout but Column. Check the difference: as I mentioned before, ColumnLayout interferes with explicit positioning and sizing. Also, you must not mix anchors and absolute positioning, especially not in the same dimension. This approach uses width and height only., no single-dimensional anchors. y is managed entirely by the Column. As the QtQuick documentation states:
anchor-based layouts cannot be mixed with absolute positioning. If an item specifies its x position and also sets anchors.left, or anchors its left and right edges but additionally sets a width, the result is undefined, as it would not be clear whether the item should use anchoring or absolute positioning. The same can be said for setting an item's y and height with anchors.top and anchors.bottom, or setting anchors.fill as well as width or height. The same applies when using positioners such as Row and Grid, which may set the item's x and y properties.
-
Hi,
thanks for the reply. I know that Layout and anchors can't be mixed, it was just to illustrate the thing. So i guess that i must either use anchors or columns/rows to position my items else it won't work at all.
The thing "strange" is that it works with visible property, so i thought that it could work too with height/width.
Thanks for everything
Sincerely