Ok definitely not know what to do so I ask for help, I've looked everywhere and can not find solution.
This is a long question involved the following files: sizeCalc.js
, main.qml
, MainForm.ui.qml
, VentPrinc.qml
and menuPrincElement.qml
, the problem is this.
Inside the file MainForm.ui.qml
have the structure of the main window which main.qml
load and run from there the logic of the UI, the content of the files is this:
MainForm.ui.qml:
import QtQuick 2.4
import QtQuick.Controls 1.3
import QtQuick.Layouts 1.1
import "sizeCalc.js" 1.0 as CalcSize
Item {
id: vent
width: CalcSize.vW; height: CalcSize.vH
property alias itemCont: itemCont
property alias vent: vent
property alias rootBarraUp: rootBarraUp
Image {
id: imgBgrnd
source: "imgSources/background.jpg"
sourceSize.height: parent.height
fillMode: Image.PreserveAspectFit
anchors.centerIn: parent
}
ColumnLayout {
id: layoutPrinc
anchors.fill: parent
Rectangle {
id: barraUpRef
height: CalcSize.barrasPrnc; width: parent.width
anchors.top: parent.top; color: "transparent"
anchors.horizontalCenter: parent.horizontalCenter
}
Item {
id: rootBarraUp; z:20
width: parent.width; anchors.top: barraUpRef.top
anchors.horizontalCenter: barraUpRef.horizontalCenter
}
Item {
id:itemContGen
anchors.top: barraUpRef.bottom; anchors.bottom: barraDown.top
width: vent.width; anchors.horizontalCenter: parent.horizontalCenter
Item {
id: itemCont
anchors.centerIn: parent
height: CalcSize.espTrbHei; width: CalcSize.espTrbWid
}
}
Rectangle {
id: barraDown
height: CalcSize.barrasPrnc; width: parent.width
anchors.bottom: parent.bottom
anchors.bottomMargin: 0
color: "white"; opacity: 0.3
}
}
states: [
State {
name: "directorio"
PropertyChanges {
target: barraDown
anchors.bottomMargin: -(height)
}
}
]
}
main.qml:
import QtQuick 2.4
import QtQuick.Controls 1.3
import QtQuick.Window 2.2
import QtQuick.Dialogs 1.2
import "sizeCalc.js" 1.0 as CalcSize
ApplicationWindow {
title: qsTr("Hello World")
width: 480
height: 640
visible: true
MainForm {
id: mainForm; anchors.fill: parent
function chVent(arg){
CalcSize.funcCambVent(arg)
}
itemCont.children: StackView {
id: stackviewPrinc; anchors.fill: parent
anchors.margins: CalcSize.espTrbDirecBordUp
initialItem: compPrinc
Component {
id: compPrinc
Loader {
id: loaderPrinc
source: "VentPrinc.qml"
Connections {
target: loaderPrinc.item.dirBoton
onClicked: CalcSize.funcCambVent(1)
}
}
}
Component {
id: compDir
Loader {
id: loaderDir
source: "Directorio.qml"
}
}
Component {
id: comp3
Loader {
id: loaderComp3
}
}
Component {
id: comp4
Loader {
id: loaderComp4
}
}
delegate: StackViewDelegate {
function transitionFinished(properties){
properties.exitItem.opacity = 1
}
pushTransition: StackViewTransition {
PropertyAnimation {
target: enterItem
property: "opacity"
from: 0; to: 1
}
PropertyAnimation {
target: exitItem
property: "opacity"
from: 1; to: 0
}
}
}
}
rootBarraUp.children: Loader {
id: barraUpLoader
anchors.top: parent.top
anchors.horizontalCenter: parent.horizontalCenter
source: "menuPrincElement.qml"
transitions: Transition {
NumberAnimation {
properties: "height, width"
easing.type: Easing.InOutQuad
}
}
}
vent.transitions: [
Transition {
NumberAnimation {
target: barraDown; duration: 500
property: "anchors.bottomMargin"
easing.type: Easing.Linear
}
}
]
}
}
VentPrinc.qml
is loaded from a StackView
within main.qml
, This is the contents of the file:
import QtQuick 2.4
import QtQuick.Layouts 1.1
import "sizeCalc.js" 1.0 as CalcSize
Item {
id: contenidoGen
anchors.top: parent.bottom; anchors.bottom: parent.top
anchors.horizontalCenter: parent.horizontalCenter
width: CalcSize.espTrbWid
property alias dirBoton: mouseAreaBotonDirPrinc
property alias turBoton: mouseAreaBotonTurPrinc
RowLayout {
id: layoutBotonesPrinc
anchors.centerIn: parent
Layout.alignment: Qt.AlignHCenter | Qt.AlignVCenter
Item {
id: botonPrincDirectorio
height: CalcSize.tamBotonesPrinc; width: height
Image {
id: imgBotonPrincDirectorio
source: "imgSources/botones/directorioBotonPrinc.png"
sourceSize.height: parent.height
fillMode: Image.PreserveAspectFit
anchors.centerIn: parent
}
MouseArea {
id: mouseAreaBotonDirPrinc
anchors.fill: parent
/*onClicked: {
mainForm.chVent(1)
}*/
}
}
Item {
id: botonPrincTurista
height: CalcSize.tamBotonesPrinc; width: height
Image {
id: imgBotonPrincTurista
source: "imgSources/botones/turistaBotonPrinc.png"
sourceSize.height: parent.height
fillMode: Image.PreserveAspectFit
anchors.centerIn: parent
}
MouseArea {
id: mouseAreaBotonTurPrinc
anchors.fill: parent
}
}
}
}
menuPrincElement.qml
is loaded from a loader
from main.qml
(this element is a top bar of the UI), and this is the contents of the file:
import QtQuick 2.4
import QtQuick.Layouts 1.1
import "sizeCalc.js" 1.0 as CalcSize
Rectangle {
property alias barraSup: barraUP
id: barraUP
height: CalcSize.barrasPrnc; width: CalcSize.vW
color: "transparent"
FontLoader { id: fontGent; source: "Aaargh.ttf" }
function chTitulo(arg){
switch(arg){
case 0: tituloItemText.state = "stPrinc"; break;
case 1: tituloItemText.state = "stDir"; break;
case 2: tituloItemText.state = "stTur"; break;
case 3: tituloItemText.state = "stConf"; break;
}
}
Rectangle {
id: backgroundMenuList; color: "white"; opacity: 0.0
anchors.fill: parent
}
Item {
id: contBarrUp
height: CalcSize.barrasPrnc; width: parent.width
anchors.top: parent.top
anchors.horizontalCenter: parent.horizontalCenter
Rectangle {
id: backgroundBarrUp; color: "white"; opacity: 0.3
anchors.fill: parent
}
Item {
id: menuItem
width: CalcSize.tamBotonMenuPrinc
height: CalcSize.tamBotonMenuPrinc
anchors.verticalCenter: parent.verticalCenter
anchors.left: parent.left
Image {
id: menuItemImg
source: "imgSources/botones/botonMenuPrinc.png"
sourceSize.height: parent.height
fillMode: Image.PreserveAspectFit
anchors.centerIn: parent
}
MouseArea {
id: menuItemMouseArea; anchors.fill: menuItem
onClicked: {
if(barraUP.state == ""){
barraUP.state = "menuOn"
}else{
barraUP.state = ""
}
}
}
}
Text {
id: tituloItemText; color: "white"
//text: CalcSize.textoTitulo;
anchors.centerIn: parent
verticalAlignment: Text.AlignVCenter
font { bold: true; pointSize: 16; family: fontGent.name }
state: "stPrinc"
states: [
State {
name: "stPrinc"
PropertyChanges { target: tituloItemText; text: "App Turista" }
},
State {
name: "stDir"
PropertyChanges { target: tituloItemText; text: "Modo Directorio" }
},
State {
name: "stTur"
PropertyChanges { target: tituloItemText; text: "Modo Turista" }
},
State {
name: "stConf"
PropertyChanges { target: tituloItemText; text: "Configuración" }
}
]
Transition {
PropertyAnimation {
target: tituloItemText
duration: 500; easing.type: Easing.InOutQuad
}
}
}
}
Item {
id: contOpcMenuGen; width: parent.width
anchors.horizontalCenter: parent.horizontalCenter
anchors.top: contBarrUp.bottom; anchors.margins: 10
anchors.bottom: barraUP.bottom; opacity: 0
ListView {
id: listaContMenuGen; anchors.fill: parent
delegate: delegateElemMenuGen
model: modelElemMenuGen
spacing: CalcSize.tamBordeElemIntLista3
}
}
Component {
id: delegateElemMenuGen
Rectangle {
id: recPrinc; color: "transparent"
anchors.margins: CalcSize.tamBordeElemIntLista2
anchors.horizontalCenter: parent.horizontalCenter
height: CalcSize.tamElemMenuPrincH
width: CalcSize.espTrbWid
Rectangle {
id: backgroundRecPrinc; color: "white"; opacity: 0.8
radius: CalcSize.tamBordeElemIntLista3
anchors.fill: recPrinc
}
MouseArea {
id: mouseAreaDelegateItem; anchors.fill: parent
onClicked: {
CalcSize.funcCambVent(model.accion)
barraUP.state = ""
}
}
Text {
id: textoElem; color: "black"; text: model.titulo
anchors.centerIn: parent
font { bold: true; family: fontGent.name; pointSize: 12 }
}
}
}
ListModel {
id: modelElemMenuGen
ListElement { titulo: "Regresar al Inicio"; accion: 0 }
ListElement { titulo: "Modo Directorio"; accion: 1 }
ListElement { titulo: "Modo Turista"; accion: 2 }
ListElement { titulo: "Configuración"; accion: 3 }
}
states: [
State {
name: "menuOn"
PropertyChanges {
target: tituloItemText; color: "#5a5a5a"
}
PropertyChanges {
target: barraUP; height: CalcSize.tamElemMenuPrincExpand
}
PropertyChanges {
target: contOpcMenuGen; opacity: 1
}
PropertyChanges {
target: backgroundBarrUp; opacity: 0.75
}
PropertyChanges {
target: backgroundMenuList; opacity: 0.7
}
}
]
transitions: [
Transition {
from: ""; to: "menuOn"
ParallelAnimation {
NumberAnimation {
target: barraUP; properties: "height"
duration: 500; easing.type: Easing.InOutQuad
}
NumberAnimation {
target: backgroundBarrUp; property: "opacity"
duration: 500; easing.type: Easing.InOutQuad
}
ColorAnimation {
target: tituloItemText; duration: 500
}
}
SequentialAnimation {
NumberAnimation {
target: backgroundMenuList; property: "opacity"
duration: 250; easing.type: Easing.InOutQuad
}
NumberAnimation {
target: contOpcMenuGen; property: "opacity"
duration: 250; easing.type: Easing.InOutQuad
}
}
},
Transition {
from: "menuOn"; to: ""
SequentialAnimation {
NumberAnimation {
target: contOpcMenuGen; property: "opacity"
duration: 250; easing.type: Easing.InOutQuad
}
NumberAnimation {
target: backgroundMenuList; property: "opacity"
duration: 250; easing.type: Easing.InOutQuad
}
}
ParallelAnimation {
NumberAnimation {
target: barraUP; properties: "height"
duration: 500; easing.type: Easing.InOutQuad
}
NumberAnimation {
targets: backgroundBarrUp; property: "opacity"
duration: 500; easing.type: Easing.InOutQuad
}
ColorAnimation {
target: tituloItemText; duration: 500
}
}
}
]
}
And finally the sezeCalc.js
file is simply a collection of functions and variables to calculate the size of the UI elements depending on the size of the window and this is the important contents of this file:
function funcCambVent(arg){
switch(arg){
case 0:
barraSup.state = ""
mainForm.state = ""
barraSup.chTitulo(0)
stackviewPrinc.push(compPrinc)
break
case 1:
barraSup.state = ""
mainForm.state = "directorio"
barraSup.chTitulo(1)
stackviewPrinc.push(compDir)
break
case 2:
barraSup.state = ""
mainForm.state = ""
barraSup.chTitulo(2)
stackviewPrinc.push(comp3)
break
case 3:
barraSup.state = ""
mainForm.state = ""
barraSup.chTitulo(3)
stackviewPrinc.push(comp4)
break
}
}
The problem is this, both VentPrinc.qml
and menuPrincElement.qml
have a MouseArea
to call a function within sizeCalc.js
which change the current "page" of StackView
this in order to go to another "window" interface while retaining various UI elements, everything works perfectly if the function is called from the menuPrincElement.qml
but to be called from VentPrinc.qml
get the error "qrc: /sizeCalc.js: 16: ReferenceError: barraSup is not defined"
I have tried everything I can to change the way in which the function is called but the error persists only when called from VentPrinc.qml
, try connecting a signal from VentPrinc.qml
to call a function in main.qml
and that this function call the function sizeCalc.js
also perform Connections from the Loader VentPrinc.qml
located in the StackView
of main.qml
also I used property alias
of the affected items from sizeCalc.js
... well I do not know what else try to always get the same error "ReferenceError: barraSup is not defined"
This error only happens when the signal is coming from VentPrinc.qml
, please if anyone knows what I'm doing wrong I'd appreciate it very much, thank you very much for your attention and I hope your answers.
PS: I apologize for grammatical errors but this is a google translation, my grammar in English is not so good.
PD2: I left some parts of the code comented or unused of other solutions I have tried.
I found the solution, being honest I have no idea why this solution works, but it works, if anyone can explain this would be helpful for those it encounters this kind of problem.
Change of function in the sizeCalc.js
file:
function funcCambVent(arg){
switch(arg){
case 0:
barraUpLoader.item.state = ""
mainForm.state = ""
barraUpLoader.item.chTitulo(0)
stackviewPrinc.push(compPrinc)
break
case 1:
barraUpLoader.item.state = ""
mainForm.state = "directorio"
barraUpLoader.item.chTitulo(1)
stackviewPrinc.push(compDir)
break
case 2:
barraUpLoader.item.state = ""
mainForm.state = ""
barraUpLoader.item.chTitulo(2)
stackviewPrinc.push(comp3)
break
case 3:
barraUpLoader.item.state = ""
mainForm.state = ""
barraUpLoader.item.chTitulo(3)
stackviewPrinc.push(comp4)
break
}
}
And VentPrinc.qml
root element instead of Item
I is replaced by Rectangle
and rename the file to ventPrinc.qml
, in this file is no longer necessary to connect in any way special function within sizeCalc.js
, simply call the function directly, the final version of this file:
import QtQuick 2.4
import QtQuick.Layouts 1.1
import "sizeCalc.js" 1.0 as CalcSize
Rectangle {
id: contenidoGen; color: "transparent"
anchors.top: parent.bottom; anchors.bottom: parent.top
anchors.horizontalCenter: parent.horizontalCenter
width: CalcSize.espTrbWid
property alias dirBoton: mouseAreaBotonDirPrinc
property alias turBoton: mouseAreaBotonTurPrinc
RowLayout {
id: layoutBotonesPrinc
anchors.centerIn: parent
Layout.alignment: Qt.AlignHCenter | Qt.AlignVCenter
Item {
id: botonPrincDirectorio
height: CalcSize.tamBotonesPrinc; width: height
Image {
id: imgBotonPrincDirectorio
source: "imgSources/botones/directorioBotonPrinc.png"
sourceSize.height: parent.height
fillMode: Image.PreserveAspectFit
anchors.centerIn: parent
}
MouseArea {
id: mouseAreaBotonDirPrinc
anchors.fill: parent
onClicked: CalcSize.funcCambVent(1)
}
}
Item {
id: botonPrincTurista
height: CalcSize.tamBotonesPrinc; width: height
Image {
id: imgBotonPrincTurista
source: "imgSources/botones/turistaBotonPrinc.png"
sourceSize.height: parent.height
fillMode: Image.PreserveAspectFit
anchors.centerIn: parent
}
MouseArea {
id: mouseAreaBotonTurPrinc
anchors.fill: parent
}
}
}
}
Besides this it is not necessary to use property alias dirBoton: mouseAreaBotonDirPrinc
.
The final StackView
in main.qml
is:
itemCont.children: StackView {
id: stackviewPrinc; anchors.fill: parent
anchors.margins: CalcSize.espTrbDirecBordUp
initialItem: compPrinc
Component {
id: compPrinc
Loader { id: loaderPrinc; source: "ventPrinc.qml" }
}
Component {
id: compDir
Loader { id: loaderDir; source: "ventDir.qml" }
}
Component {
id: comp3
Loader { id: loaderTur }
}
Component {
id: comp4
Loader { id: loaderConf }
}
}