Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. QML and Qt Quick
  4. How Can I update data in my list model

How Can I update data in my list model

Scheduled Pinned Locked Moved Solved QML and Qt Quick
3 Posts 2 Posters 2.1k Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • S Offline
    S Offline
    Subuday
    wrote on last edited by
    #1

    I have a list model. I change the data, but changes don't displayes. (I want to make changes from C++ side)

    class ProblemListModel: public QAbstractListModel
    {
        Q_OBJECT
    
    public:
        enum Roles {
           IDRole = Qt::UserRole + 1,
           NameRole,
           DesctiptionRole
        };
    
        ProblemListModel (QObject *parent = 0);
    
        virtual int rowCount(const QModelIndex &parent) const;
        virtual QVariant data(const QModelIndex &index, int role) const;
        virtual QHash<int, QByteArray> roleNames() const;
    
        Q_INVOKABLE void add(const Problem &unit);
        Q_INVOKABLE void update(const int &index, const Problem &unit);
        Q_INVOKABLE void remove(const int &index);
        void clear();
    
    private:
        QList <Problem> m_data;
    };
    
    #include "problemlistmodel.h"
    
    ProblemListModel::ProblemListModel(QObject *parent)
    {
    
    }
    
    int ProblemListModel::rowCount(const QModelIndex &parent) const
    {
        if (parent.isValid()) {
            return 0;
        }
    
        return m_data.size();
    }
    
    QVariant ProblemListModel::data(const QModelIndex &index, int role) const
    {
        if (!index.isValid()) {
            return QVariant();
        }
    
        switch (role) {
        case IDRole:
            return m_data.at(index.row()).id;
        case NameRole:
            return m_data.at(index.row()).name;
        case DesctiptionRole:
            return m_data.at(index.row()).description;
        default:
            return QVariant();
        }
    }
    
    QHash<int, QByteArray> ProblemListModel::roleNames() const
    {
        QHash<int, QByteArray> roles = QAbstractListModel::roleNames();
        roles[IDRole] = "problemID";
        roles[NameRole] = "name";
        roles[DesctiptionRole] = "description";
    
        return roles;
    }
    
    void ProblemListModel::add(const Problem &unit)
    {
        beginInsertRows(QModelIndex(), m_data.size(), m_data.size());
        m_data.append(unit);
        endInsertRows();
    }
    
    void ProblemListModel::update(const int &index, const Problem &unit)
    {
        qDebug() << index;
        qDebug() << unit.name;
        m_data.replace(index, unit);
    
        //emit dataChanged(parent, parent);
    }
    
    void ProblemListModel::remove(const int &index)
    {
        beginRemoveRows(QModelIndex(), index, index);
        endRemoveRows();
        m_data.removeAt(index);
    }
    
    void ProblemListModel::clear()
    {
        beginRemoveRows(QModelIndex(), 0, m_data.size());
        endRemoveRows();
        m_data.clear();
    }
    
    void Storage::updateUserProblemSlot(const QVariantMap &data)
    {
        int index = data.value("index").toInt();
        Problem problem;
        problem.id = data.value("problemID").toInt();
        problem.name = data.value("name").toString();
        problem.description = data.value("description").toString();
        problemListModel.update(index, problem);
    }
    
    KillerSmathK 1 Reply Last reply
    0
    • S Subuday

      I have a list model. I change the data, but changes don't displayes. (I want to make changes from C++ side)

      class ProblemListModel: public QAbstractListModel
      {
          Q_OBJECT
      
      public:
          enum Roles {
             IDRole = Qt::UserRole + 1,
             NameRole,
             DesctiptionRole
          };
      
          ProblemListModel (QObject *parent = 0);
      
          virtual int rowCount(const QModelIndex &parent) const;
          virtual QVariant data(const QModelIndex &index, int role) const;
          virtual QHash<int, QByteArray> roleNames() const;
      
          Q_INVOKABLE void add(const Problem &unit);
          Q_INVOKABLE void update(const int &index, const Problem &unit);
          Q_INVOKABLE void remove(const int &index);
          void clear();
      
      private:
          QList <Problem> m_data;
      };
      
      #include "problemlistmodel.h"
      
      ProblemListModel::ProblemListModel(QObject *parent)
      {
      
      }
      
      int ProblemListModel::rowCount(const QModelIndex &parent) const
      {
          if (parent.isValid()) {
              return 0;
          }
      
          return m_data.size();
      }
      
      QVariant ProblemListModel::data(const QModelIndex &index, int role) const
      {
          if (!index.isValid()) {
              return QVariant();
          }
      
          switch (role) {
          case IDRole:
              return m_data.at(index.row()).id;
          case NameRole:
              return m_data.at(index.row()).name;
          case DesctiptionRole:
              return m_data.at(index.row()).description;
          default:
              return QVariant();
          }
      }
      
      QHash<int, QByteArray> ProblemListModel::roleNames() const
      {
          QHash<int, QByteArray> roles = QAbstractListModel::roleNames();
          roles[IDRole] = "problemID";
          roles[NameRole] = "name";
          roles[DesctiptionRole] = "description";
      
          return roles;
      }
      
      void ProblemListModel::add(const Problem &unit)
      {
          beginInsertRows(QModelIndex(), m_data.size(), m_data.size());
          m_data.append(unit);
          endInsertRows();
      }
      
      void ProblemListModel::update(const int &index, const Problem &unit)
      {
          qDebug() << index;
          qDebug() << unit.name;
          m_data.replace(index, unit);
      
          //emit dataChanged(parent, parent);
      }
      
      void ProblemListModel::remove(const int &index)
      {
          beginRemoveRows(QModelIndex(), index, index);
          endRemoveRows();
          m_data.removeAt(index);
      }
      
      void ProblemListModel::clear()
      {
          beginRemoveRows(QModelIndex(), 0, m_data.size());
          endRemoveRows();
          m_data.clear();
      }
      
      void Storage::updateUserProblemSlot(const QVariantMap &data)
      {
          int index = data.value("index").toInt();
          Problem problem;
          problem.id = data.value("problemID").toInt();
          problem.name = data.value("name").toString();
          problem.description = data.value("description").toString();
          problemListModel.update(index, problem);
      }
      
      KillerSmathK Offline
      KillerSmathK Offline
      KillerSmath
      wrote on last edited by
      #2

      @Subuday
      You need to notify the view that a model's data has been changed. This behavior is reached when you emit the dataChanged signal.

      See the signature of this signal:

      dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight, const QVector<int> &roles)
      

      You need to pass two QModelIndex (topLeft and bottomRight). that is the boundary of the change, and also, need to pass the roles of data that need to be changed on view.

      See a example of how it could be implemented.

      void ProblemListModel::update(int row, const Problem &unit) // row number
      {
          qDebug() << row;
          qDebug() << unit.name;
          m_data.replace(row, unit);
          QVector<int> roles = {IDRole, NameRole, DesctiptionRole};
          
         // use index function to get the QModelIndex that represents the row
      emit dataChanged(index(row, 0), index(row, 0), roles); // only change the index(row,column)
      }
      

      @Computer Science Student - Brazil
      Web Developer and Researcher
      “Sometimes it’s the people no one imagines anything of who do the things that no one can imagine.” - Alan Turing

      S 1 Reply Last reply
      2
      • KillerSmathK KillerSmath

        @Subuday
        You need to notify the view that a model's data has been changed. This behavior is reached when you emit the dataChanged signal.

        See the signature of this signal:

        dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight, const QVector<int> &roles)
        

        You need to pass two QModelIndex (topLeft and bottomRight). that is the boundary of the change, and also, need to pass the roles of data that need to be changed on view.

        See a example of how it could be implemented.

        void ProblemListModel::update(int row, const Problem &unit) // row number
        {
            qDebug() << row;
            qDebug() << unit.name;
            m_data.replace(row, unit);
            QVector<int> roles = {IDRole, NameRole, DesctiptionRole};
            
           // use index function to get the QModelIndex that represents the row
        emit dataChanged(index(row, 0), index(row, 0), roles); // only change the index(row,column)
        }
        
        S Offline
        S Offline
        Subuday
        wrote on last edited by
        #3

        @KillerSmath Thank you!

        1 Reply Last reply
        0

        • Login

        • Login or register to search.
        • First post
          Last post
        0
        • Categories
        • Recent
        • Tags
        • Popular
        • Users
        • Groups
        • Search
        • Get Qt Extensions
        • Unsolved