Reputation: 414
I develop a small qt application using QML. I'd like to show a list of clickable items there. I have IssueHolder class derived from QObject to represent the item to visualize there. I created a model for such items
class IssuesModel : public QAbstractListModel
{
Q_OBJECT
public:
IssuesModel(QObject *parent = 0);
int rowCount(const QModelIndex &parent = QModelIndex()) const override;
QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override;
const QList<IssueHolder*>& issues() const { return _issues; }
protected:
QHash<int, QByteArray> roleNames() const override;
private: //Members
QList<IssueHolder*> _issues;
};
In the view class I set my model to the qml part like this
_view = new QQuickView;
_mainSetModel = new IssuesModel(this);
_view->rootContext()->setContextProperty("mainSetModel", _mainSetModel);
After that I created delegate in my QML file
ListView {
// Some properties here
model: mainSetModel
delegate: Item {
// Some properties here
IssueDelegate {
id: issuesDelegate
// Some properties here
signal pressed()
MouseArea {
onClicked: { issuesDelegate.pressed(); }
}
}
}
}
I'd like to do something when my list item is clicked but I don't want to implement the application logic in QML file. So I'd like to react on delegate click action so that if user click on some item on my list view corresponding IssueHolder instance will be notified. How can I do this?
Upvotes: 0
Views: 842
Reputation: 24416
You could declare a IssueHolder
role in your model:
enum {
IssueHolderRole = Qt::UserRole
};
Then, reimplement roleNames()
:
QHash<int, QByteArray> IssuesModel::roleNames() const
{
QHash<int, QByteArray> names;
names.insert(IssueHolderRole, "issueHolder");
return names;
}
You'll also need to account for the new role in your data()
function. The documentation has lots of examples of how to do this, but the gist of it is:
if (role == IssueHolderRole)
return QVariant::fromValue(_issues.at(index.row()));
In IssueHolder
, declare an invokable function or slot:
Q_INVOKABLE void doStuff();
In your delegate, respond to the click:
delegate: Item {
// Some properties here
IssueDelegate {
id: issuesDelegate
// Some properties here
MouseArea {
onClicked: model.issueHolder.doStuff()
}
}
}
Upvotes: 0