QSortFilterProxyModel not mapping properly
-
I'm having an issue with calls to a QSortFilterProxyModel's mapFromSource function always returning an invalid QModelIndex, regardless of the index provided. In my test case, the model has exactly 1 valid entry, but regardless of what QModelIndex I provide, it always returns invalid. Below is some of the test code I've been using.
auto src = _sorted_view->sourceModel(); for (int i = 0; i < src->rowCount(QModelIndex()); ++i) { for (int j = 0; j < src->columnCount(QModelIndex()); ++j) { QModelIndex s = src->index(i, j); QModelIndex m = _meta_model->index(i, j); QModelIndex v = _sorted_view->mapFromSource(s); QModelIndex t = _sorted_view->mapFromSource(m); std::string st = src->data(s).toString().toStdString(); std::string mt = _meta_model->data(m).toString().toStdString(); if (v.isValid()) { //Always invalid std::string vt = _sorted_view->data(v).toString().toStdString(); } if (t.isValid()) { //Always invalid std::string tt = _sorted_view->data(t).toString().toStdString(); } } }
In this case, _sorted_view is the QSortFilterProxyModel and _meta_model is a subclass of QAbstractItemModel. Would anyone with a better understanding of QT's model-view setup be able to tell me why the mapping here is not working? As a note, calls to mapToSource generate perfectly valid QModelIndexes, but trying to go the other way does not.
-
Hi and welcome to devnet,
Why are you using indexes from two different models and map them with
_sorted_view
? -
Are you sure of that ? Because if they point to the same object, then the index returned should be the same. If not, then your custom model does something wrong.
-
Can you show how the source model is implemented ?
-
Yes, here's the top level class. There's a handful of subclasses but I don't believe they do interactions with the Model/View aspects.
class CxFVariableItemModel : public QAbstractItemModel { public: CxFVariableItemModel () : QAbstractItemModel () { } virtual ~CxFVariableItemModel () {} const QList <QString> &headers () const { return _headers; } virtual const QList <QString> &possibleHeaders () const = 0; void setHeaders (const QList <QString> &headers) { emit layoutAboutToBeChanged (); _headers = headers; emit layoutChanged (); } virtual const bool useLabels (int whichSensor) = 0; virtual const QList <LabelReturnType> &getUsefulStrings (bool returnLabels, int whichSensor) = 0; virtual const char *getVariableName (int whichSensor) = 0; virtual const int getWhichRow (const char *name) = 0; virtual const int depVarSize (int whichSensor, int i) = 0; virtual const char *getRealDependName (const int whichSensor, const int whichDependSensor) = 0; /// Will return a list of all possible timing variable names virtual const QList <QString> getListOfTimingVariableNames () = 0; /// Will return a list of all possible variable names virtual const QList <QString> getListOfVariableNames () = 0; QModelIndex index (int row, int column, const QModelIndex &parent = QModelIndex ()) const { if (!hasIndex (row, column, parent)) { return QModelIndex (); } if (parent == QModelIndex ()) { return createIndex(row, column); } if (_headers [column] == "Other") { return createIndex (row, column, reinterpret_cast <void *> (parent.row () + 1)); } return QModelIndex (); } QModelIndex parent (const QModelIndex &index) const { // We used to have index.parent ().row () but that causes an issue when we only had one variable in the GUI. long parentRow = index.row (); if (parentRow == 0) return QModelIndex (); else { return createIndex (parentRow - 1, 0); } } virtual int rowCount (const QModelIndex &parent) const = 0; int columnCount (const QModelIndex &) const { return _headers.size (); } virtual QVariant data (const QModelIndex &index, int role = Qt::DisplayRole) const = 0; QVariant headerData (int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const { if (role == Qt::DisplayRole) { if (orientation == Qt::Horizontal) { return QVariant (_headers [section]); } else { // vertical return (QVariant (section)); } } return (QVariant ()); } protected : QList <QString> _headers; };
Some of this code is quite old so it may not necessarily be correct according to current Qt Model/View standards which is where I think the problem lies.
-
You can check you model implementation with the QAbstractItemModelTester. See this wiki entry.