Global position of Rectangle



  • Hi.

    I have a simple, but somehow "ungoogable", question.

    I have a Rectangle and a Window (QtQuick.Window 2.0)

    When you click on the rectangle a window should appear beneath the rectangle

    How do I get the "global position (x, y)" of the rectangle so I can position the window beneath it? As the window is not an Item you cannot use the "mapFromItem() or mapToItem()" functions!



  • Hi,

    You could use mouse area properties.
    mouseX and mouseY delivers the current mouse position.



  • Thanks for your reply, but as stated in the "documentation":http://qt-project.org/doc/qt-5.0/qtquick/qml-qtquick2-mousearea.html#mouseX-prop:
    "The coordinates are relative to the MouseArea."

    P.s. been on holiday, hence my slow reply - sorry.


  • Moderators

    Hi,

    I think you will get to access those functions from cpp class from where your QML gets called .
    For e.g in Qt Quick 2.0 from QtQuick2ApplicationViewer class



  • Maybe.

    However, I think that it would require that the rectangle is within the main window.
    I, unfortunately, open a new window via QML and it is within this window my problem sits. Maybe I need to do a "Qt hack" and create the window from c++ and hide it until needed. I should then be able to get the coordinates of that window and from there calculate the rectangle position?


  • Moderators

    Yes. Maybe. Can you post your QML code ? And also how it is called ?



  • Yes. I've tried to limit the code for simplification :)
    Inside the "SettingsSection" is where I try to open another "dropdown window". Here, however, I cannot get the global position of the rectangle resided inside a "SettingsSection" (a "SettingsSection" is just a rectangle with images, buttons etc.)

    I think I might have to give up the idea of using the QtQuick.Window for the ComboBox, and then just let the rectangle grow (will loose the shadow and have to battle with z order (guess I can set in in an onclick event))

    Notes:

    • The widget window is a wrapper made due old code base that this code will eventually be moved to
    • I cannot use Qt's ComboBox and style it, as you cannot style the list (so the "button" is nice, but the dropdown is the ugliest thing mankind have yet seen)

    Main.cpp
    @#include <QApplication>
    #include "widgetwindow.h"

    int main(int argc, char *argv[])
    {
    QApplication a(argc, argv);

    WidgetWindow toolbarContainer;
    toolbarContainer.show();
    
    return a.exec&#40;&#41;;
    

    }@

    WidgetWindow.cpp
    @#include <QHBoxLayout>
    #include <QMargins>

    #include <QQuickItem>
    #include <QtQuick/QQuickView>

    WidgetWindow::WidgetWindow(QWidget *parent) :
    QWidget(parent)
    {
    initWindow();

    //Load the qml file into a QWidget
    QQuickView *view = new QQuickView();
    QWidget *container = QWidget::createWindowContainer(view, this);
    container->resize(500, 50);
    container->setFocusPolicy(Qt::TabFocus);
    view->setSource(QUrl::fromLocalFile&#40;"..\\..\\ITW_Toolbar\\QML\\Toolbar\\Toolbar.qml"&#41;);
    
    //Use the BoxLayout to make the qml fill the form
    QHBoxLayout *layout = new QHBoxLayout;
    layout->setSpacing(0);
    layout->setMargin(0);
    layout->addWidget(container);
    
    //Get the width of the screen
    int screenWidth = getScreenWidth();
    
    //Set the layout, move (include frame)
    this->setLayout(layout);
    this->move(0 + (this->x() - this->geometry().x()), 0 + (this->y() - this->geometry().y()) );
    
    //resize the form (Qt HACK with resizing for redraw)
    this->resize(screenWidth, 40);
    QObject *rootObject = dynamic_cast<QObject*>(view->rootObject());
    rootObject->setProperty("width", screenWidth);
    
    //Signals
    connectQmlSignals(view);
    

    }@

    Toolbar.QML
    @Rectangle
    {
    id: itwToolbar
    width: Screen.desktopAvailableWidth
    height: 42
    color: "white"

    signal quit;
    
    Flow
    {
        id: buttonContainer
        anchors.verticalCenter: parent.verticalCenter
        anchors.horizontalCenter: parent.horizontalCenter
        spacing: 10
    
        ...
    }
    
    //The settings window that is a QtQuick.Window 2.0 (opens like a drop-down beneath the toolbar (centered)
    SettingsComponents.SettingsWindow {
        id: settingsWindow
        x: (buttonContainer.x + (buttonContainer.width / 2)) - (settingsWindow.width / 2)
        y: itwToolbar.height
    }
    

    }@

    SettingsWindow.QML
    @DropDownWindow {
    openedHeight: 400
    width: 500
    color: "white"
    ...

    //
    //Profile section
    //
    SettingsHeader {
        ...
    }
    
    SettingsSection {
        ...
    }
    
    SettingsSection {
        ...
    }
    
    //
    //Reader section
    //
    SettingsHeader {
        ...
    }
    
    SettingsSection {
        ...
    }
    
    SettingsSection {
        ...
    }
    
    ...@
    

    DropDownWindow.QML
    @import QtQuick 2.0
    import QtQuick.Controls 1.0
    import QtQuick.Window 2.0

    Window {
    id: dropDownWindow
    width: 100
    height: 400//dropDownWindow.childrenRect.height + 6

    property int openedHeight: 100
    
    visible: false
    flags: Qt.Popup | Qt.WindowStaysOnTopHint
    
    Behavior on height { NumberAnimation { id: heightAnimation; easing.type: Easing.OutQuad; duration: 400 } }
    
    function hide()
    {
        height = 0;
    }
    
    function show()
    {
        height = openedHeight;
    }
    
    Rectangle {
        id: borderRect
        color: "white"
        anchors.fill: parent        
    
        border.color: "black"
        border.width: 1
    

    }@

    SettingsSection.QML
    @Rectangle {
    id: sectionRect
    ...

    Windows8_ComboBox {
        id: sectionSelectionComboBox
        ...
    }
    

    }@
    Windows8_ComboBox
    @import QtQuick 2.0

    Rectangle {
    height: 25
    width: 100
    color: "white"

    border {
        color: "lightgray"
        width: 1
    }
    
    property string currentSelection: "select"
    
    Text{
        ...
    }
    
    Image{
        ...
    }
    
    MouseArea{
        anchors.fill: parent
        hoverEnabled: true
        onEntered: parent.color = "lightblue"
        onExited: parent.color = "white"
        onClicked: {            
                dropDownList.height == dropDownList.openedHeight ? dropDownList.hide() : dropDownList.show()
        }
    }
    
    DropDownWindow {
        id: dropDownList
        width: parent.width
        height: 100
        openedHeight: 100
    
        visible: false
    }
    
    Component.onCompleted:
    {
        //What to do?
        dropDownList.x = x
        dropDownList.y = height
    }
    

    }@


  • Moderators

    Hi,

    As far as i understand from your code is you want to show a window like a dropdown when you click "Windows8_ComboBox" item. Is it so ? So can't you use "anchors.top" property and anchor it to bottom of "Windows8_ComboBox" ? In this way it will move along as the width of main window also increases.



  • Yes, that is correct. I am making my own dropdown/combobox implementation as the one in Qt is not Windows 8 like.

    Anchors is not a part of a QtQuick.Window so that is, unfortunately, not an option...


  • Moderators

    Yes. If you are not using QtQuick.Window ofcourse.
    A better option would be a ListView in your case as it will be scrollable if you have more items in it.



  • Yes. I'm also thinking of going for the ListView or some other form. However this will have the disadvantage that the list will not show outside the parent and that I have to fix the z-order issue when having multiple controlls... the latter should be manageable.


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.