2016-04-14 30 views
0

我有2個qml文件。 Toolbarbutton.qml創建一個按鈕,DockWidget.qml創建一個ListView。我正在嘗試將Toolbarbutton中的按鈕廣播到DockWidget,該按鈕已被點擊。然後我想添加項目到我的listView。無法獲取2個使用信號進行通信的QML文件

我一直在嘗試使用信號來建立通信。在Toolbarbutton.qml中,我有一個ID爲saveButton的Rectangle項目。在這個矩形項下,我添加了一個名爲addSaveHistory()的信號。我縮短了代碼,所以更容易看到我在做什麼。

Rectangle { 
id: saveButton 
width: 50 
height: 30 
border.color: "white" 
color: buttonMouseArea.containsMouse ? "grey" : "black" 

//Button text 
Text{ 
    id: buttonLabel 
    anchors.centerIn: parent 
    text: "Save +" 
    color: "white" 
} 
signal addSaveHistory(string url) 

MouseArea{ 
    id: buttonMouseArea 
    anchors.fill: parent //anchor the mousearea to the rect area 

    //onClicked handles valid mouse button clicks 
    onClicked: { 
     addSaveHistory("Hello?") //dispatch the event 

    } 
} 
} 

在DockWidget.qml文件中,我有一個使用Connections組件的項目。我縮短了代碼,因此更容易看到我在做什麼。

Item{ 
    width: 100 
    height: 100 
    objectName: "Save + History" 

Rectangle { 
    id: rect 
    anchors.fill: parent 
    color: "#323232" 

Connections { 
    target: saveButton //id of rectangle in ToolbarButton.qml 

    onAddSaveHistory: { 

     // this is never called 
    } 
} 
} 

我似乎無法弄清楚爲什麼onAddSaveHistory永遠不會被調用。我也曾嘗試使用Loader組件將Dockwidget.qml文件加載到Toolbarbutton.qml中,然後專門在Dockwidget中調用一個函數,但那不起作用。

我對信號的工作原理有錯誤的想法嗎?我會非常感謝任何指導。

這是我的main.qml文件。

所有的
import QtQuick 2.2 
import Painter 1.0 

import "save.js" as Save 

Plugin { 

//executed at startup 
Component.onCompleted:{ 

    //add toolbar 
    alg.ui.addToolBarWidget("ToolbarButton.qml")//add a button to toolbar 
    alg.ui.addDockWidget("DockWidget.qml")//add dock widget 

    Save.log("Incremental Save Plugin has been created") 

    } 
} 

回答

1

首先,認識到,信號在ToolbarButton.qml文件的根,即矩形聲明的QML元件上。只有根項目形成了QML元素的接口。所有的孩子元素都被外界隱藏起來。所以通常在文件頂部附近聲明信號。一個常見的排序是:

Item { 
    id: root 
    property real foo: 0.0 
    property alias bar: innerItem.bar 
    signal baz(url location) 

    Rectangle { 
     id: innerItem 
     property color bar: "red" 
    } 
} 

因此,在這種情況下,一個簡單的ToolbarButton.qml聲明的信號,當你在一個包含鼠標區域單擊看起來像這樣發出的:

import QtQuick 2.3 

Rectangle { 
    id: root 
    width: buttonLabel.width + 20 
    height: buttonLabel.height + 20 
    color: "steelBlue" 

    // Declare signal on the button object 
    signal addSaveHistory(string url) 

    Text { 
     id: buttonLabel 
     anchors.centerIn: parent 
     text: "Save +" 
    } 

    MouseArea { 
     id: buttonMouseArea 
     anchors.fill: parent 
     onClicked: { 
      // emit the signal 
      root.addSaveHistory("Hello?") 
     } 
    } 
} 

那麼簡單這個信號的消費者,這裏只是一個文本元素,但可以是任何東西,可能是這樣的:

import QtQuick 2.3 

Text { 
    id: dockWidget 
    text: "Waiting for a click..." 
} 

別急,你說,這是如何的幫助。到目前爲止,沒有任何聯繫。當我們實例化我們的接收器項目時,我們做到這一點。因此,在這裏,main.qml文件如下所示:

import QtQuick 2.3 
import QtQuick.Window 2.2 

Window { 
    visible: true 

    // Instantiate the ToolbarButton that emits the signal when clicked 
    ToolbarButton { 
     id: toolbarButton 
     anchors.top: parent.top 
     anchors.left: parent.left 
     anchors.topMargin: 10 
     anchors.leftMargin: 10 
    } 

    // Instantiate the DockWidget (just a Text element in this example) 
    DockWidget { 
     id: dockWidget 
     anchors.bottom: parent.bottom 
     anchors.bottomMargin: 10 
     anchors.left: parent.left 
     anchors.leftMargin: 10 

     // Complete the plumbing that connects the signal from item above 
     // with id: toolbarButton. 
     Connections { 
      target: toolbarButton 
      // When signal addSaveHistory is emitted, 
      // replace binding above with a new one 
      onAddSaveHistory: dockWidget.text = "Button was clicked" 
     } 
    } 
} 

實際上,沒有必要將Connections元素作爲DockWidget的子元素。將ToolbarButton和Dock小部件想象成樂高積木,我們在一個對這些項目有更高層次知識以及他們應該如何交互的位置上進行溝通。如果你想要,你可以把它包裝到自己更復雜的定製QML組件中。

此外,如果你只對信號有一點愛心,你甚至都不需要連接元素都:

import QtQuick 2.3 
import QtQuick.Window 2.2 

Window { 
    visible: true 

    ToolbarButton { 
     id: toolbarButton 
     anchors.top: parent.top 
     anchors.left: parent.left 
     anchors.topMargin: 10 
     anchors.leftMargin: 10 

     // Add signal handler directly to emitter 
     onAddSaveHistory: dockWidget.text = "Button was clicked" 
    } 

    DockWidget { 
     id: dockWidget 
     anchors.bottom: parent.bottom 
     anchors.bottomMargin: 10 
     anchors.left: parent.left 
     anchors.leftMargin: 10 
    } 
} 

希望這有助於。

+0

嗨肖恩, 非常感謝您的幫助。我有一個獨特的問題,因爲我正在使用qml爲另一個使用qml創建接口的應用程序創建一個插件。如你所建議的,我無法設置我的main.qml。這是我的main.qml需要格式化的方式。我編輯了我的原始帖子以顯示main.qml。 – WesM

+0

我編輯了ToolbarButton.qml,按照您的建議工作,以便將其放置在矩形項目下,然後使用id.signalFucntion()語法調用信號。 但是,它似乎是我試圖建立的連接並不知道ToolbarButton.qml中的信號 – WesM

+0

沒有看到alg.ui.addToolBarWidget()和alg.ui.addDockWidget()是否難以說出解決方案是什麼。我猜測他們實例化了作爲參數傳入的QML文件。不知何故,您需要能夠引用那些能夠使用插件{}範圍內的Connections {}元素。您可能需要查看這些功能的文檔(我還找不到任何公開的內容),或詢問編寫這些功能的開發人員是否有典型示例。 –