universallistmodel.h 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114
  1. #ifndef UNIVERSALLISTMODEL_H
  2. #define UNIVERSALLISTMODEL_H
  3. #include <QAbstractListModel>
  4. #include <QObject>
  5. #include <QList>
  6. #include <QHash>
  7. #include <QPointer>
  8. #include <QMetaProperty>
  9. #include <QMetaObject>
  10. #include <QDebug>
  11. template <typename T>
  12. class UniversalListModel : public QAbstractListModel
  13. {
  14. public:
  15. UniversalListModel(QObject* parent = 0) : QAbstractListModel(parent) {}
  16. ~UniversalListModel() {
  17. clear();
  18. }
  19. int rowCount(const QModelIndex &parent) const {
  20. Q_UNUSED(parent)
  21. return m_container.count();
  22. }
  23. QHash<int, QByteArray> roleNames() const {
  24. if(s_roleNames.isEmpty()) {
  25. int propertyCount = T::staticMetaObject.propertyCount();
  26. for(int i = 1; i < propertyCount; i++) {
  27. s_roleNames.insert(Qt::UserRole + i, T::staticMetaObject.property(i).name());
  28. }
  29. s_roleNames[propertyCount] = "modelData";
  30. }
  31. return s_roleNames;
  32. }
  33. QVariant data(const QModelIndex &index, int role) const
  34. {
  35. int row = index.row();
  36. if(row < 0 || row >= m_container.count() || m_container.at(row).isNull()) {
  37. return QVariant();
  38. }
  39. T* dataPtr = m_container.at(row).data();
  40. if(s_roleNames.value(role) == "modelData") {
  41. return QVariant::fromValue(dataPtr);
  42. }
  43. return dataPtr->property(s_roleNames.value(role));
  44. }
  45. bool add(T* value) {
  46. Q_ASSERT_X(value != nullptr, fullTemplateName(), "Trying to add member of NULL");
  47. if(m_container.indexOf(value) >= 0) {
  48. #ifdef DEBUG
  49. qDebug() << fullTemplateName() << "Member already exists";
  50. #endif
  51. return false;
  52. }
  53. beginInsertRows(QModelIndex(), m_container.count(), m_container.count());
  54. m_container.append(QPointer<T>(value));
  55. endInsertRows();
  56. return true;
  57. }
  58. void remove(T* value) {
  59. Q_ASSERT_X(value != nullptr, fullTemplateName(), ": Trying to remove member of NULL");
  60. int valueIndex = m_container.indexOf(value);
  61. if(valueIndex >= 0) {
  62. beginRemoveRows(QModelIndex(), valueIndex, valueIndex);
  63. m_container.removeAt(valueIndex);
  64. endRemoveRows();
  65. }
  66. }
  67. void reset(const QList<QPointer<T> >& container) {
  68. beginResetModel();
  69. clear();
  70. m_container = container;
  71. endResetModel();
  72. }
  73. protected:
  74. void clear() {
  75. //TODO: need to verify if wee really should cleanup these commits.
  76. // foreach (const QPointer<T>& value, m_container) {
  77. // if(!value.isNull()) {
  78. // delete value.data();
  79. // }
  80. // }
  81. m_container.clear();
  82. }
  83. QList<QPointer<T> > m_container;
  84. static QHash<int, QByteArray> s_roleNames;
  85. private:
  86. static QByteArray fullTemplateName() { //Debug helper
  87. return QString("UniversalListModel<%1>").arg(T::staticMetaObject.className()).toLatin1();
  88. }
  89. };
  90. template<typename T>
  91. QHash<int, QByteArray> UniversalListModel<T>::s_roleNames;
  92. #endif // UNIVERSALLISTMODEL_H