Home > OS >  QML ComboBox model can't be filled using Javascript using append()
QML ComboBox model can't be filled using Javascript using append()

Time:02-03

I'm using Qt 5.15.2 LTS for developing.

Suppose I have following ComboBox:

ComboBox {
    id: myComboBox

    ListModel {
        id: myModel
    }

    model: myModel
    delegate: ItemDelegate {
        text: name
    }

    Component.onCompleted: {
        myModel.append({ "name": "1", "value": "val1" });
        myModel.append({ "name": "2", "value": "val2" });
        myModel.append({ "name": "3", "value": "val3" });
        myModel.append({ "name": "4", "value": "val4" });
    }
}

When compiling my application, I get the following GUI output:

empty ComboBox

The ComboBox is just empty - however when calling console.log("model.count: " myModel.count) in Component.onCompleted, I get the output qml: model.count: 4 so the model seems to be filled but somehow the contents are not displayed.

However, when substituting ComboBox with ListView:

ListView {
    id: myComboBox

    ListModel {
        id: myModel
    }

    model: myModel
    delegate: ItemDelegate {
        text: name
    }

    Component.onCompleted: {
        myModel.append({ "name": "1", "value": "val1" });
        myModel.append({ "name": "2", "value": "val2" });
        myModel.append({ "name": "3", "value": "val3" });
        myModel.append({ "name": "4", "value": "val4" });
    }
}

I am getting the deserved output:

filled ListView

According to the QML ComboBox docs, the ComboBox should be perfectly fine being populated with a ListModel:

ComboBox {
    currentIndex: 2
    model: ListModel {
        id: cbItems
        ListElement { text: "Banana"; color: "Yellow" }
        ListElement { text: "Apple"; color: "Green" }
        ListElement { text: "Coconut"; color: "Brown" }
    }
    width: 200
    onCurrentIndexChanged: console.debug(cbItems.get(currentIndex).text   ", "   cbItems.get(currentIndex).color)
}

How come the behaviors differ so much? What do I have to do to fill my ComboBox in a proper way using Javascript?

CodePudding user response:

Try to set the currentIndex property. This is coming from the documentation:

currentIndex

The default value is -1 when count is 0, and 0 otherwise.

My guess is because you are adding the items to the model after the creation of the ComboBox the currentIndex keeps its intial value of -1, hence nothing is selected. When you open the ComboBox you can see the values, but by default none is selected.

Also another thing I did was to add the textRole property. You should also add the valueRole property. I've tested it with both Qt 5.15.11 and 6.4.0.

You should read the paragraph ComboBox Model Roles.

ComboBox {
    id: myComboBox

    ListModel {
        id: myModel
    }

    textRole: "name"
    currentIndex: 0

    model: myModel
    delegate: ItemDelegate {
        text: name
    }

    Component.onCompleted: {
        myModel.append({ "name": "1", "value": "val1" });
        myModel.append({ "name": "2", "value": "val2" });
        myModel.append({ "name": "3", "value": "val3" });
        myModel.append({ "name": "4", "value": "val4" });
    }
}

CodePudding user response:

There's no real need to change the delegate just to display your content. It is enough to set textRole: "name". As a recommendation, it is generally best to separate the UI and non-UI components, so, I have moved the ListModel and Component.onCompleted to the bottom of the file:

import QtQuick
import QtQuick.Controls
Page {
    ComboBox {
        id: myComboBox
        model: myModel
        textRole: "name"
    }
    ListModel {
        id: myModel
    }
    Component.onCompleted: {
        myModel.append({ "name": "1", "value": "val1" });
        myModel.append({ "name": "2", "value": "val2" });
        myModel.append({ "name": "3", "value": "val3" });
        myModel.append({ "name": "4", "value": "val4" });
    }
}

You can Try it Online!

  • Related