Silex
Silex

Reputation: 2713

How can I access QSortFilterProxyModel elements in QML outside of a ListView

I have a QSortFilterProxyModel which is accessible from my QML code. I am using it in a ListView in my QML code, but I also would like to access the first element of it outside of my ListView.

Let's say I call my QSortFilterProxyModel sortedObjects. In the ListView I just pass it to the model property, like model: sortedObjects and then in the delegate property I can access it's roles, by the specified role names. How can I do this outside of a ListView? Something like sortedObjects[0].someRoleName.

Upvotes: 4

Views: 3246

Answers (2)

Silex
Silex

Reputation: 2713

As @mcchu pointed out in his post, there is a function called index and data in QSortFilterProxyModel. Unfortunately if I try to call these functions on my QSortFilterProxyModel in QML, then I get the following error:

TypeError: Property 'index' of object QSortFilterProxyModel(0x7fcff0c2af90) is not a function

Therefore as this post suggested. I have created a separate C++ class, which receives a const pointer of my QSortFilterProxyModel and creates a function, which then wraps the index and data functions and returns the desired value. This class is registered so it can be called from QML code.

Here is the code:

class SomeClass : public QObject {
    Q_OBJECT
public:
    SomeClass(const QSortFilterProxyModel* sortedModel) {
        m_sortedModel = sortedModel;
    }

    Q_INVOKABLE QVariant getValue() {
        QVariant someTypeRole = m_sortedModel->data(m_sortedModel->index(0, 0), SomeModelClass::SomeRoles::SomeTypeRole);
        if (someTypeRole.isValid()) {
            return type = someTypeRole.toString(); // I know it is a QString for sure, but there are mechanisms to find out the type of the role
        }

        return QVariant();
    }

private:
    const QSortFilterProxyModel* m_sortedModel;
};

EDIT:

As @Mitch pointed out in his comment @mcchu's solution works, but only from Qt 5.5.

Upvotes: 1

mcchu
mcchu

Reputation: 3369

QSortFilterProxyModel is a QAbstractItemModel. And in QAbstractItemModel, you can access the element in the model by calling two Q_INVOKABLE functions in QML:

  1. index to get a QModelIndex, and then
  2. data to get the value of a role in that index

For example, assume that the hash value of someRoleName is 1234 (defined in the roleNames in your model). You can get the value of someRoleName in row 0 (and column 0 if the model is a list) like the following function in QML:

function printSomeRoleNameInRow0()
{
    var row = 0, col = 0, someRoleName = 1234;
    var idx = sortedObjects.index(row, col);
    var value = sortedObjects.data(idx, someRoleName);
    console.log(value);
}

Upvotes: 4

Related Questions