如何将动态内容放入QML组件中

时间:2014-02-18 20:39:29

标签: qt qml qt5

我在使用QML创建可扩展组件时遇到了很多麻烦。有些技术可行,但我想做的是这样的事情:

//Outline.qml
Rectangle {
  color: 'red'
  //Children are inserted here
}

//main.qml
Rectangle {
  ... 
  Outline {
    Text { I'm trying to inject this into the Outline component
      text: "Hi I'm the inner text!"
    }
  }
}

我知道我可以通过使用Loader组件并将sourceComponent设置为Component实例来实现此目的,但是当我做任何中等复杂的事情时(例如可重用的对话框)我的编写函数和引用子组件实例的能力受到了阻碍。如果组件在同一个QML文件中实例化,那么id / function关系就可以了,我可以直接引用我的文本字段。

以下是加载程序的示例:

//Outline.qml
Rectangle {
  id : root
  color: 'red'
  property Component content;
  Loader {
    source : root.content
  }
}

//main.qml
Rectangle {
  function getData(){
     return inner.getData(); 
     //ERROR inner is undefined because it is created by the Loader instance.
  }
  ... 
  Outline {
    content: Component {
        TextField {
          id: inner
          function getData(){
            return inner.text || 'none';
          }
        }
    }
  }
}

我希望有一个更好的方法来处理它。我知道我可以直接在父级内部构建一个Component并获得顶级引用,但它不允许我正在寻找的控制级别。在这种情况下,组件的“静态”扩展将是更可取的。

编辑:这是一个说明问题的QML示例。点击输出是: ReferenceError: getMe is not defined

import QtQuick 2.2
import QtQuick.Controls 1.0
import QtQuick.Layouts 1.1

Item {
    id: app
    width: 640
    height: 480

    function accessData(){
        output.text = getMe.text
    }

    Loader {
        width: parent.width
        height: 300
        sourceComponent: Component {
            Rectangle {
                anchors.fill: parent
                color: 'yellow'

                TextField {
                    anchors.centerIn: parent
                    id: getMe
                    placeholderText: 'Input data...'
                }
            }
        }
    }


    Button {
        id: button
        y: app.height - 50
        text: 'get data'
        onClicked: {
            accessData();
        }
    }

    Text {
        y: app.height - button.height
        id: output
        text: 'none'
    }
}

正如您在使用“loader”方法时所看到的那样,sourceComponent不属于同一个树(您无法访问内部数据)。

1 个答案:

答案 0 :(得分:2)

这是针对问题的说明性示例的有效工作解决方案,稍后会在您的项目中进行尝试

  1. 为您的Loader提供一个ID:“ id:yourLoader ”以及加载器ex中的矩形:“ id:yourRect

  2. 将一个String 属性添加到yourRect,它将保存您的TextField.text

    Loader { id: yourLoader
             width: parent.width
             height: 300
             sourceComponent: Component {
    
         Rectangle {
                     property string yourText : getMe.text
                     id: yourRect
                     anchors.fill: parent
                     color: 'yellow'
    
            TextField {
                anchors.centerIn: parent
                id: getMe
                placeholderText: 'Input data...'
            }
        }
      }
    }
    
  3. 我们更改了您的函数accessData

     function accessData(){
                    var rect= yourLoader.item //we get yourRect from the loader 
                     output.text = rect.yourText // yourText <-- getMe.text
    
     }