Trying to center items in a ColumnLayout (nested into a StackLayout) but doesn't seem to work.
The StackLayout contains also a Canvas which I used to verify that Layout.fillWidth: true is working as expected. So I assume also the ColumnLayout is filling width (i.e. the problem is not the outer StackLayout), although I cannot understand what problem it has.
import QtQuick 2.15
import QtQuick.Window 2.15
import QtQuick.Controls 2.15
import QtQuick.Layouts 1.3
Window {
id: mainWindow
width: 340
height: 380
visible: true
title: qsTr("Hello")
TabBar {
id: tabBar
width: parent.width
TabButton {text: "Layout"}
TabButton {text: "Canvas"}
}
StackLayout {
anchors.fill: parent
anchors.topMargin: tabBar.height
currentIndex: tabBar.currentIndex
ColumnLayout {
Layout.fillWidth: true
spacing: 10
Label {
Layout.alignment: Qt.AlignCenter
text: "Regular buttons:"
}
RowLayout {
Layout.alignment: Qt.AlignCenter
spacing: 10
Button {text: "Normal"}
Button {text: "Highlighted"; highlighted: true}
DelayButton {text: "Delay"}
}
Label {
Layout.alignment: Qt.AlignCenter
text: "Checkboxes:"
}
RowLayout {
Layout.alignment: Qt.AlignCenter
spacing: 10
CheckBox {text: "Checkbox 1"}
CheckBox {text: "Checkbox 2"}
}
Label {
Layout.alignment: Qt.AlignCenter
text: "Radiobuttons:"
}
RowLayout {
Layout.alignment: Qt.AlignCenter
spacing: 10
RadioButton {text: "Radiobutton 1"}
RadioButton {text: "Radiobutton 2"}
}
Label {
Layout.alignment: Qt.AlignCenter
text: "Miscellaneous:"
}
Switch {
Layout.alignment: Qt.AlignCenter
text: "Switch"
}
}
Canvas {
Layout.fillWidth: true
Layout.fillHeight: true
Layout.maximumHeight: 100
Layout.margins: 2
onPaint: {
var ctx = getContext('2d')
ctx.reset()
ctx.strokeStyle = 'black'
ctx.lineWidth = 2
ctx.beginPath()
ctx.moveTo(0, 0)
ctx.lineTo(width, height)
ctx.stroke()
ctx.beginPath()
ctx.moveTo(width, 0)
ctx.lineTo(0, height)
ctx.stroke()
}
}
}
}
Related
How can i make the buttons wrap when a dialog window is resized to be narrow by the user? Currently they are just cutoff.
QML
import QtQuick 2.7
import QtQuick.Controls 2.0
import QtQuick.Layouts 1.0
Frame {
width: parent.width
height: parent.height
ColumnLayout {
width: implicitWidth
spacing: 20
anchors.left: parent.left
anchors.right: parent.right
Layout.alignment: Qt.AlignTop
// Config
ColumnLayout {
Layout.fillWidth: true
spacing: 2
Label {
text: "Config"
font.bold: true
}
TextField {
readOnly: true
placeholderText: qsTr("Path to config.json file (C:\\desktop\\config.txt)")
Layout.fillWidth: true
}
RowLayout {
Layout.fillWidth: true
Layout.alignment: Qt.AlignRight
Button {
text: qsTr("Edit")
implicitWidth: implicitHeight
}
Button {
text: qsTr("Browse")
implicitWidth: implicitHeight
}
Button {
text: qsTr("Clear")
implicitWidth: implicitHeight
}
Button {
text: qsTr("Find")
implicitWidth: implicitHeight
}
}
}
// File
ColumnLayout {
Layout.fillWidth: true
spacing: 2
Label {
text: "File"
font.bold: true
}
TextField {
readOnly: true
placeholderText: qsTr("Path to config.json file (C:\\desktop\\file.txt)")
Layout.fillWidth: true
}
RowLayout {
Layout.fillWidth: true
Layout.alignment: Qt.AlignRight
Button {
text: qsTr("Clear")
implicitWidth: implicitHeight
}
Button {
text: qsTr("Find")
implicitWidth: implicitHeight
}
}
}
}
}
main.qml
import QtQuick 2.7
import QtQuick.Controls 2.0
import QtQuick.Layouts 1.0
ApplicationWindow {
visible: true
width: 640
height: 480
title: qsTr("Hello World")
Page1 {
anchors.centerIn: parent
}
}
You have to use Flow instead of RowLayout:
import QtQuick 2.7
import QtQuick.Controls 2.0
import QtQuick.Layouts 1.0
Frame {
width: parent.width
height: parent.height
ColumnLayout {
width: implicitWidth
spacing: 20
anchors.left: parent.left
anchors.right: parent.right
Layout.alignment: Qt.AlignTop
// Config
ColumnLayout {
Layout.fillWidth: true
spacing: 2
Label {
text: "Config"
font.bold: true
}
TextField {
readOnly: true
placeholderText: qsTr("Path to config.json file (C:\\desktop\\config.txt)")
Layout.fillWidth: true
}
Flow {
Layout.fillWidth: true
layoutDirection: Qt.RightToLeft
Button {
text: qsTr("Edit")
implicitWidth: implicitHeight
}
Button {
text: qsTr("Browse")
implicitWidth: implicitHeight
}
Button {
text: qsTr("Clear")
implicitWidth: implicitHeight
}
Button {
text: qsTr("Find")
implicitWidth: implicitHeight
}
}
}
// File
ColumnLayout {
Layout.fillWidth: true
spacing: 2
Label {
text: "File"
font.bold: true
}
TextField {
readOnly: true
placeholderText: qsTr("Path to config.json file (C:\\desktop\\file.txt)")
Layout.fillWidth: true
}
Flow {
Layout.fillWidth: true
layoutDirection: Qt.RightToLeft
Button {
text: qsTr("Clear")
implicitWidth: implicitHeight
}
Button {
text: qsTr("Find")
implicitWidth: implicitHeight
}
}
}
}
}
Lets suppose i have an application that has items that can get bigger than it's window height.
How can i make it so it will show a vertical scrollbar only if needed?
I will show now what is happening on a test application i've done.
When all the items are closed:
When the items are opened:
Here the scrollbar should appear.
I will post now the code i've used for this example:
main.qml
import QtQuick 2.7
import QtQuick.Dialogs 1.2
import QtQuick.Layouts 1.3
import QtQuick.Controls 2.3
import QtQuick.Window 2.3
ApplicationWindow {
visible: true
width: 640
height: 200
title: qsTr("Tabbars")
Rectangle{
anchors.fill:parent
Column {
anchors.fill: parent
PanelItem {
id:panel1
title: "Panel 1"
width:parent.width
content: Item {
property string title: "teste"
height: configContent.implicitHeight
width: configContent.implicitWidth
ColumnLayout{
id:configContent
anchors.topMargin: 10
anchors.bottomMargin: 10
anchors.fill:parent
TextField {
id: companyNameText1
placeholderText: qsTr("Company name")
Layout.fillWidth: true
selectByMouse: true
}
ComboBox {
id: languagesComboBox1
textRole: "text"
objectName: "language"
Layout.fillWidth: true
model: ListModel {
ListElement {text: QT_TR_NOOP("English"); oid: 0}
ListElement {text: QT_TR_NOOP("Portuguese"); oid: 1}
ListElement {text: QT_TR_NOOP("Spanish"); oid: 2}
ListElement {text: QT_TR_NOOP("Italian"); oid: 3}
ListElement {text: QT_TR_NOOP("French"); oid: 4}
ListElement {text: QT_TR_NOOP("Portuguese(Brasil)"); oid: 5}
}
}
ComboBox {
id: devSndrModeComboBox1
textRole: "text"
objectName: "test_dev_sndr_mode"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("None"), oid: 0 })
append({ text: QT_TR_NOOP("Subpanel"), oid: 1 })
append({ text: QT_TR_NOOP("All"), oid: 2 })
}
}
}
}
}
Component.onCompleted: {
console.log("panel 1 height "+panel1.height)
}
}
PanelItem {
id:panel2
title: "Panel 2"
width:parent.width
content: Item {
property string title: "teste"
height: configContent2.implicitHeight
width: configContent2.implicitWidth
ColumnLayout{
id:configContent2
anchors.fill:parent
ComboBox {
id: sndrModeComboBox1
textRole: "text"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("Preset"), oid: 0 })
append({ text: QT_TR_NOOP("Programmed"), oid: 1 })
}
}
}
}
}
Component.onCompleted: {
console.log("panel 2 height "+panel2.height)
}
}
PanelItem {
id:panel3
title: "Panel 3"
width:parent.width
content: Item {
property string title: "teste"
height: configContent3.implicitHeight
width: configContent3.implicitWidth
ColumnLayout{
id:configContent3
anchors.fill:parent
ComboBox {
id: sndrModeComboBox2
textRole: "text"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("Preset"), oid: 0 })
append({ text: QT_TR_NOOP("Programmed"), oid: 1 })
}
}
}
}
}
Component.onCompleted: {
console.log("panel 2 height "+panel2.height)
}
}
PanelItem {
id:panel4
title: "Panel 4"
width:parent.width
content: Item {
property string title: "teste"
height: configContent4.implicitHeight
width: configContent4.implicitWidth
ColumnLayout{
id:configContent4
anchors.fill:parent
ComboBox {
id: sndrModeComboBox3
textRole: "text"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("Preset"), oid: 0 })
append({ text: QT_TR_NOOP("Programmed"), oid: 1 })
}
}
}
}
}
Component.onCompleted: {
console.log("panel 2 height "+panel2.height)
}
}
PanelItem {
id:panel5
title: "Panel 4"
width:parent.width
content: Item {
property string title: "teste"
height: configContent5.implicitHeight
width: configContent5.implicitWidth
ColumnLayout{
id:configContent5
anchors.fill:parent
ComboBox {
id: sndrModeComboBox4
textRole: "text"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("Preset"), oid: 0 })
append({ text: QT_TR_NOOP("Programmed"), oid: 1 })
}
}
}
}
}
Component.onCompleted: {
console.log("panel 2 height "+panel2.height)
}
}
PanelItem {
id:panel6
title: "Panel 5"
width:parent.width
content: Item {
property string title: "teste"
height: configContent6.implicitHeight
width: configContent6.implicitWidth
ColumnLayout{
id:configContent6
anchors.fill:parent
ComboBox {
id: sndrModeComboBox5
textRole: "text"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("Preset"), oid: 0 })
append({ text: QT_TR_NOOP("Programmed"), oid: 1 })
}
}
}
}
}
Component.onCompleted: {
console.log("panel 2 height "+panel2.height)
}
}
}
}
}
PanelItem.qml
import QtQuick 2.7
import QtQuick.Layouts 1.2
Item {
id: root
property Component content
property string title: "panel"
property bool isSelected: false
height: container.height + bar.height
Rectangle{
id: bar
anchors {
top: parent.top
left: parent.left
right: parent.right
}
height: 30
color: root.isSelected ? "#81BEF7" : "#CEECF5"
Text {
anchors.fill: parent
anchors.margins: 10
horizontalAlignment: Text.AlignLeft
verticalAlignment: Text.AlignVCenter
text: root.title
}
Text {
anchors{
right: parent.right
top: parent.top
bottom: parent.bottom
margins: 10
}
horizontalAlignment: Text.AlignRight
verticalAlignment: Text.AlignVCenter
text: "^"
rotation: root.isSelected ? "180" : 0
}
MouseArea {
anchors.fill: parent
cursorShape: Qt.PointingHandCursor
onClicked: isSelected = !isSelected
}
}
Rectangle{
id: container
anchors.top: bar.bottom
anchors.left: parent.left
anchors.right: parent.right
height: loader.item && isSelected ? loader.item.height : 0
Loader {
id: loader
visible: isSelected
sourceComponent: content
anchors.top: container.top
}
Behavior on height {
PropertyAnimation { duration: 100 }
}
}
}
How can a scrollbarimplemented so it is called only when needed?
I hope this might help.
ScrollView {
id: scrollView // This is just an ID of scroll view
width: 300 // This is the width of the scroll view window
height: 300 // This is the height of the scroll view window
// contentHeight or contentWidth holds the value of the whole
// content height which needs a scroll bar if it is larger
// than the height or width of the ScrollView
// childrenRect.width returns the highest width among the children.
// childrenRect.height returns the highest height among the children.
contentWidth: childrenRect.width
contentHeight: childrenRect.height
// This is false by default.
// This hides the excess content behind the boundaries of ScrollView; the height and the width
clip: true
// enter your contents here
}
Import QtQuick.Controls 2.14 or higher versions to support contentWidth and contentHeight
I've found what i believe is a really good solution.
The scrollbar this way will only appear if needed:
Item{
id:item
anchors.fill:parent
ScrollView{
anchors.fill:parent
Column {
width:item.width
}
}
}
This maybe a silly question, but im developing an accordion like component, where i pass with the property content the contents i want it to have.
the problem is when i click on the element when it opens i'm not finding how i can get the height of those items.
An example when its closed:
example when open:
Here we see that panel 2 component should go down
The code in main.qml is:
import QtQuick 2.7
import QtQuick.Dialogs 1.2
import QtQuick.Layouts 1.3
import QtQuick.Controls 2.3
import QtQuick.Window 2.3
ApplicationWindow {
visible: true
width: 640
height: 480
title: qsTr("Tabbars")
Rectangle{
anchors.fill:parent
PanelItem {
id:panel1
title: "Panel 1"
anchors.top:parent.top
anchors.left:parent.left
anchors.right:parent.right
content: Item {
property string title: "teste"
anchors.fill:parent
height:configContent.implicitHeight
ColumnLayout{
id:configContent
anchors.fill:parent
TextField {
id: companyNameText1
placeholderText: qsTr("Company name")
Layout.fillWidth: true
selectByMouse: true
}
ComboBox {
id: languagesComboBox1
textRole: "text"
objectName: "language"
Layout.fillWidth: true
model: ListModel {
ListElement {text: QT_TR_NOOP("English"); oid: 0}
ListElement {text: QT_TR_NOOP("Portuguese"); oid: 1}
ListElement {text: QT_TR_NOOP("Spanish"); oid: 2}
ListElement {text: QT_TR_NOOP("Italian"); oid: 3}
ListElement {text: QT_TR_NOOP("French"); oid: 4}
ListElement {text: QT_TR_NOOP("Portuguese(Brasil)"); oid: 5}
}
}
ComboBox {
id: devSndrModeComboBox1
textRole: "text"
objectName: "test_dev_sndr_mode"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("None"), oid: 0 })
append({ text: QT_TR_NOOP("Subpanel"), oid: 1 })
append({ text: QT_TR_NOOP("All"), oid: 2 })
}
}
}
}
}
Component.onCompleted: {
resetOtherAccordions.connect(panel2.resetHeight)
console.log("panel 1 height "+panel1.height)
}
}
PanelItem {
id:panel2
title: "Panel 2"
anchors.topMargin: 5
anchors.top:panel1.bottom
anchors.left:parent.left
anchors.right:parent.right
content: Item {
property string title: "teste"
anchors.fill:parent
height:configContent2.implicitHeight
ColumnLayout{
id:configContent2
anchors.fill:parent
ComboBox {
id: sndrModeComboBox1
textRole: "text"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("Preset"), oid: 0 })
append({ text: QT_TR_NOOP("Programmed"), oid: 1 })
}
}
}
}
}
Component.onCompleted: {
resetOtherAccordions.connect(panel1.resetHeight)
console.log("panel 2 height "+panel2.height)
}
}
}
}
the code in PanelItem.qml
import QtQuick 2.7
import QtQuick.Layouts 1.2
Item {
default property var contentItem: null
property Component content
property string title: "panel"
id: root
height: 30
property bool current: false
signal resetOtherAccordions()
function resetHeight(){
root.children[0].children[1].visible = false
root.children[0].children[1].height = 0
root.current = false
}
Rectangle {
id: bar
anchors.top:root.top
anchors.left:root.left
anchors.right:root.right
height: 30
color: root.current ? "#81BEF7" : "#CEECF5"
Text {
anchors.fill: parent
anchors.margins: 10
horizontalAlignment: Text.AlignLeft
verticalAlignment: Text.AlignVCenter
text: root.title
}
Text {
anchors{
right: parent.right
top: parent.top
bottom: parent.bottom
margins: 10
}
horizontalAlignment: Text.AlignRight
verticalAlignment: Text.AlignVCenter
text: "^"
rotation: root.current ? "180" : 0
}
MouseArea {
anchors.fill: bar
cursorShape: Qt.PointingHandCursor
onClicked: {
root.current = !root.current; //toggle ao current
resetOtherAccordions()
if(root.current) {
root.children[1].visible = true
root.children[1].height = root.children[1].children[0].children[0].height
console.log("childrenRect height of: "+root.children[1].children[0].children[0].height)//gives 0
console.log("height of: "+root.children[1].children[0].children[0].childrenRect.height)//gives 0
console.log("title of: "+root.children[1].children[0].children[0].title)//gives teste
root.height = 30+root.children[1].height
}
else {
root.children[1].visible = false
root.children[1].height = 0
root.height = 30
}
}
}
}
Rectangle {
id: container
anchors.top:bar.bottom
anchors.left:root.left
anchors.right:root.right
color:"white"
height:0
visible:false
Loader {
id: yourLoader
anchors.fill:container
anchors.top:container.top
sourceComponent: root.content
}
Behavior on height {
PropertyAnimation { duration: 100 }
}
}
}
What am i missing? thanks
I see that you are complicating yourself too much, the basic idea is that the height of the PanelItem is the height of the content plus the bar, and that with the loader you hide the content when necessary.
PanelItem.qml
import QtQuick 2.7
import QtQuick.Layouts 1.2
Item {
id: root
property Component content
property string title: "panel"
property bool isSelected: false
height: container.height + bar.height
Rectangle{
id: bar
anchors {
top: parent.top
left: parent.left
right: parent.right
}
height: 30
color: root.isSelected ? "#81BEF7" : "#CEECF5"
Text {
anchors.fill: parent
anchors.margins: 10
horizontalAlignment: Text.AlignLeft
verticalAlignment: Text.AlignVCenter
text: root.title
}
Text {
anchors{
right: parent.right
top: parent.top
bottom: parent.bottom
margins: 10
}
horizontalAlignment: Text.AlignRight
verticalAlignment: Text.AlignVCenter
text: "^"
rotation: root.isSelected ? "180" : 0
}
MouseArea {
anchors.fill: parent
cursorShape: Qt.PointingHandCursor
onClicked: isSelected = !isSelected
}
}
Rectangle{
id: container
anchors.top: bar.bottom
anchors.left: parent.left
anchors.right: parent.right
height: loader.item && isSelected ? loader.item.height : 0
Loader {
id: loader
visible: isSelected
sourceComponent: content
anchors.top: container.top
}
Behavior on height {
PropertyAnimation { duration: 100 }
}
}
}
main.qml
import QtQuick 2.7
import QtQuick.Controls 2.3
import QtQuick.Layouts 1.3
ApplicationWindow {
id: root
visible: true
width: 640
height: 480
title: qsTr("Tabbars")
Rectangle{
anchors.fill:parent
Column{
anchors.fill: parent
PanelItem{
width: parent.width
title: "Panel 1"
content: Item {
property string title: "teste"
height: configContent.implicitHeight
width: configContent.implicitWidth
ColumnLayout{
id:configContent
width: root.width
//anchors.fill:parent
TextField {
id: companyNameText1
placeholderText: qsTr("Company name")
Layout.fillWidth: true
selectByMouse: true
}
ComboBox {
id: languagesComboBox1
textRole: "text"
objectName: "language"
Layout.fillWidth: true
model: ListModel {
ListElement {text: QT_TR_NOOP("English"); oid: 0}
ListElement {text: QT_TR_NOOP("Portuguese"); oid: 1}
ListElement {text: QT_TR_NOOP("Spanish"); oid: 2}
ListElement {text: QT_TR_NOOP("Italian"); oid: 3}
ListElement {text: QT_TR_NOOP("French"); oid: 4}
ListElement {text: QT_TR_NOOP("Portuguese(Brasil)"); oid: 5}
}
}
ComboBox {
id: devSndrModeComboBox1
textRole: "text"
objectName: "test_dev_sndr_mode"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("None"), oid: 0 })
append({ text: QT_TR_NOOP("Subpanel"), oid: 1 })
append({ text: QT_TR_NOOP("All"), oid: 2 })
}
}
}
}
}
}
PanelItem{
width: parent.width
title: "Panel 1"
content: Item {
property string title: "teste"
height:configContent2.implicitHeight
width: configContent2.implicitWidth
ColumnLayout{
id:configContent2
width: root.width
ComboBox {
id: sndrModeComboBox1
textRole: "text"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("Preset"), oid: 0 })
append({ text: QT_TR_NOOP("Programmed"), oid: 1 })
}
}
}
}
}
}
}
}
}
To explain better the question, im going to use images, but in summary i'll have a component that will transition the heightfrom 0 to an height that is correspondent to the height of it's childs. that problem is that all the child itemswill appear the moment the transition starts
To illustrate, the height of the child div of Panel 1is 0:
then i click, the transition is supposed to take 5000ms and this happens:
at the end of the 5000ms i have this:
The code i've used for this example is this:
main.qml
import QtQuick 2.7
import QtQuick.Dialogs 1.2
import QtQuick.Layouts 1.3
import QtQuick.Controls 2.3
import QtQuick.Window 2.3
ApplicationWindow {
visible: true
width: 640
height: 200
title: qsTr("Tabbars")
Item{
id:item
anchors.fill:parent
ScrollView{
anchors.fill:parent
Column {
width:item.width
PanelItem {
id:panel1
title: "Panel 1"
width:parent.width
content: Item {
property string title: "teste"
height: configContent.implicitHeight
width: configContent.implicitWidth
ColumnLayout{
id:configContent
anchors.topMargin: 10
anchors.bottomMargin: 10
anchors.fill:parent
TextField {
id: companyNameText1
placeholderText: qsTr("Company name")
Layout.fillWidth: true
selectByMouse: true
}
ComboBox {
id: languagesComboBox1
textRole: "text"
objectName: "language"
Layout.fillWidth: true
model: ListModel {
ListElement {text: QT_TR_NOOP("English"); oid: 0}
ListElement {text: QT_TR_NOOP("Portuguese"); oid: 1}
ListElement {text: QT_TR_NOOP("Spanish"); oid: 2}
ListElement {text: QT_TR_NOOP("Italian"); oid: 3}
ListElement {text: QT_TR_NOOP("French"); oid: 4}
ListElement {text: QT_TR_NOOP("Portuguese(Brasil)"); oid: 5}
}
}
ComboBox {
id: devSndrModeComboBox1
textRole: "text"
objectName: "test_dev_sndr_mode"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("None"), oid: 0 })
append({ text: QT_TR_NOOP("Subpanel"), oid: 1 })
append({ text: QT_TR_NOOP("All"), oid: 2 })
}
}
}
}
}
}
PanelItem {
id:panel2
title: "Panel 2"
width:parent.width
content: Item {
property string title: "teste"
height: configContent2.implicitHeight
width: configContent2.implicitWidth
ColumnLayout{
id:configContent2
anchors.fill:parent
ComboBox {
id: sndrModeComboBox1
textRole: "text"
Layout.fillWidth: true
model: ListModel {
Component.onCompleted: {
append({ text: QT_TR_NOOP("Preset"), oid: 0 })
append({ text: QT_TR_NOOP("Programmed"), oid: 1 })
}
}
}
}
}
}
}
}
}
}
and PanelItem.qml
import QtQuick 2.7
import QtQuick.Layouts 1.2
Item {
id: root
property Component content
property string title: "panel"
property bool isSelected: false
height: container.height + bar.height
Rectangle{
id: bar
anchors {
top: parent.top
left: parent.left
right: parent.right
}
height: 30
color: root.isSelected ? "#81BEF7" : "#CEECF5"
Text {
anchors.fill: parent
anchors.margins: 10
horizontalAlignment: Text.AlignLeft
verticalAlignment: Text.AlignVCenter
text: root.title
}
Text {
anchors{
right: parent.right
top: parent.top
bottom: parent.bottom
margins: 10
}
horizontalAlignment: Text.AlignRight
verticalAlignment: Text.AlignVCenter
text: "^"
rotation: root.isSelected ? "180" : 0
}
MouseArea {
anchors.fill: parent
cursorShape: Qt.PointingHandCursor
onClicked: isSelected = !isSelected
}
}
Rectangle{
id: container
anchors.top: bar.bottom
anchors.left: parent.left
anchors.right: parent.right
height: loader.item && isSelected ? loader.item.height : 0
Loader {
id: loader
visible: isSelected
sourceComponent: content
anchors.top: container.top
}
Behavior on height {
PropertyAnimation { duration: 5000 }
}
}
}
I hope i explained well the problem.
What would be the best way to solve this?
I have a simple login form written in QML with a custom component, MediumText, and two TextFields. Unfortunately, I'm not able to properly align the elements, as shown by the following picture:
I want the labels to the left (MediumText type), as well as the TextField instances on the right, to take up the same amount of space so that they are correctly aligned. Can you suggest me an approach? Here is my current code.
MediumText.qml:
import QtQuick 2.3
Text {
clip: true
font.pixelSize: 20
font.family: "Liberation Mono"
smooth: true
font.bold: true
wrapMode: Text.WordWrap
opacity: 1
}
Login.qml:
import QtQuick 2.4
import QtQuick.Controls 1.3
import QtQuick.Window 2.2
import QtQuick.Dialogs 1.2
import QtQuick.Layouts 1.1
Rectangle {
id:rootRect
anchors.centerIn: parent
Layout.preferredWidth: 480
Layout.preferredHeight: 640
ColumnLayout {
anchors.centerIn: parent
Layout.fillWidth: true
spacing: 16
Row{
Image {
id: logoimage
height: 135
fillMode: Image.PreserveAspectFit
source: "images/logo.png"
}
}
RowLayout {
anchors.left: parent.left; anchors.right: parent.right
spacing: 4
MediumText { text: "Username: ";Layout.fillWidth:true; }
TextField { id:usernameText; placeholderText: "username"; Layout.fillWidth: true;}
}
RowLayout {
anchors.left: parent.left; anchors.right: parent.right
spacing: 4
MediumText { text: "Password:";Layout.fillWidth:true }
TextField { id:passwordText; placeholderText: "password"; echoMode: TextInput.Password; Layout.fillWidth: true;}
}
RowLayout {
spacing: 16
anchors.horizontalCenter: parent.horizontalCenter
Button { text: "Login"; onClicked: {
console.log(mojoLoginLoader.visible);
mojoLoginLoader.visible=true;
passwordText.enabled=false;
usernameText.enabled=false;
//auth_controller.sayHello();
mojoRootViewHolder.source="Welcome.qml"
}
}
Button { text: "Exit"; onClicked: auth_controller.sayNay() }
}
}
CenteredLoader{visible:false; id:mojoLoginLoader}
}
One fix that works is setting the preferredWidth property of the TextField:
MediumText { text: "Username: ";Layout.fillWidth:true;Layout.preferredWidth: parent.width/2}
You can use a GridLayout instead of building a grid by means of ColumnLayout and RowLayout.
By using the GridLayout, what you want is already guaranteed by the component.
Here is a full example from which you can start:
import QtQuick 2.3
import QtQuick.Window 2.2
import QtQuick.Controls 1.2
import QtQuick.Layouts 1.1
Window {
visible: true
width: 500
height: 500
title: "Grid example"
ColumnLayout {
anchors.centerIn: parent
Layout.fillWidth: true
spacing: 16
Row{
Image {
id: logoimage
height: 135
fillMode: Image.PreserveAspectFit
source: "images/logo.png"
}
}
GridLayout {
anchors.centerIn: parent
Layout.fillWidth: true
columnSpacing: 16
rowSpacing: 4
columns: 2
MediumText { text: "Username: "; Layout.fillWidth:true; }
TextField { id:usernameText; placeholderText: "username"; Layout.fillWidth: true;}
MediumText { text: "Password:";Layout.fillWidth:true }
TextField { id:passwordText; placeholderText: "password"; echoMode: TextInput.Password; Layout.fillWidth: true;}
}
RowLayout {
spacing: 16
anchors.horizontalCenter: parent.horizontalCenter
Button { text: "Login"; onClicked: {
console.log(mojoLoginLoader.visible);
mojoLoginLoader.visible=true;
passwordText.enabled=false;
usernameText.enabled=false;
//auth_controller.sayHello();
mojoRootViewHolder.source="Welcome.qml"
}
}
Button { text: "Exit"; onClicked: auth_controller.sayNay() }
}
}
}