代码之家  ›  专栏  ›  技术社区  ›  drahnr

给定填充的ro QList的Qt模型视图

  •  0
  • drahnr  · 技术社区  · 14 年前

    xyz QList (大到哪里都可以移动)。如何为其创建模型视图?我已经阅读了Qt文档,它告诉我,我必须重新实现 data index , parent rowCount , columnCount 功能。但是预处理器/编译器需要更多的重新实现的函数?我已经读过Qt书中的一章了,但也没用。这里是我的黑客代码:

    class XModel : public QAbstractListModel
    {
    Q_OBJECT
    public:
        explicit XModel(QList<int> *valuelist, QObject *parent = 0);
        virtual ~XModel();
        int rowCount(const QModelIndex &) const;
        int columnCount(const QModelIndex &) const;
        QModelIndex index( int row, int column, const QModelIndex & parent = QModelIndex()) const;
        QModelIndex parent(const QModelIndex &index) const;
        QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
    private:
        QList<int>* blah;
    signals:
    
    public slots:
    
    };
    
    
    
    XModel::XModel(QList<int> *valuelist, QObject *parent) :
        QAbstractListModel(parent),
        blah(valuelist)
    {
    
    }
    
    
    
    
    XModel::~XModel()
    {
    
    }
    
    
    
    int XModel::rowCount(const QModelIndex &) const
    {
        return blah->size();
    }
    
    int XModel::columnCount(const QModelIndex &) const
    {
        return 1;
    }
    
    
    QModelIndex XModel::index(int row, int column, const QModelIndex &parent) const
    {
        return createIndex(row, column, (void)&(blah->at(row)));
    }
    
    
    
    QModelIndex XModel::parent(const QModelIndex &index) const
    {
        return createIndex(index->row(), index->column(), NULL); 
    }
    
    
    
    
    QVariant XModel::data(const QModelIndex &index, int role = Qt::DisplayRole) const
    {
        return QVariant(blah->at(index.row()));
    }
    

    QAbstractItemModel 或者是 QAbstractListModel 数据

    这是固定的,但是。。。

    编辑:

    Widget::Widget(QWidget *parent)
        : QWidget(parent),
        valuelist(),
        xm(&valuelist) //xm = XModel
    {
        valuelist.append(1);
        valuelist.append(2);
        valuelist.append(3);
        valuelist.append(4);
        valuelist.append(5);
        valuelist.append(6);
        valuelist.append(7);
        valuelist.append(8);
        valuelist.append(9);
    
        view = new QListView(this);
        view->setModel(&xm);
        //how to force the XModel to reread the QList`?
        view->show();
    }
    
    1 回复  |  直到 12 年前
        1
  •  4
  •   Community pid    4 年前

    Widget::Widget(QWidget *parent)
        : QWidget(parent),
        valuelist(),
        xm(&valuelist) //xm = XModel
    {
        xm.append(1);
        xm.append(2);
        xm.append(3);
        xm.append(4);
        xm.append(5);
        xm.append(6);
        xm.append(7);
        xm.append(8);
        xm.append(9);
    
        view = new QListView(this);
        view->setModel(&xm);
    
        xm.append(10); // should call beginInsertRows, append to valuelist, and call endInsertRows.
    
        Q_ASSERT(valuelist.contains(10));
    
        view->show();
    }
    

    否则,您也许可以创建一个QObject和QList的组合,它可以发出信号来通知XModel更改,但我认为第一种方法更好。

    编辑:

    这是一个愚蠢的例子。它将创建一个列表支持的模型,该模型将每秒向列表添加更多元素:

    #include <QtGui/QApplication>
    #include <QtGui/QListView>
    #include <QtCore/QAbstractListModel>
    #include <QtCore/QTimer>
    
    class ListBackedModel : public QAbstractListModel
    {
        Q_OBJECT
        QList<int>* m_list;
    
    public:
    
        ListBackedModel(QList<int>* list, QObject* parent = 0)
            : QAbstractListModel(parent)
            , m_list(list)
        {}
    
        ~ListBackedModel()
        {}
    
        int rowCount(const QModelIndex &parent = QModelIndex()) const
        {
            Q_UNUSED(parent);
            return m_list->size();
        }
    
        QVariant data(const QModelIndex &index, int role) const
        {
            if (index.row() >= rowCount()) { return QVariant(); }
            if (index.row() < 0) { return QVariant(); }
    
            int element = m_list->at(index.row());
    
            if (Qt::DisplayRole == role) {
                return QString::number(element);
            }
    
            if (Qt::ToolTipRole == role) {
                return tr("%1 is element #%2").arg(element).arg(index.row() + 1);
            }
    
            return QVariant();
        }
    
        void append(int element)
        {
            /*
                First is the new index of the first element that will be inserted.
                Last is the new index of the last element that will be inserted.
                Since we're appending only one element at the end of the list, the
                index of the first and last elements is the same, and is equal to
                the current size of the list.
            */
            int first = m_list->size();
            int last = first;
    
            beginInsertRows(QModelIndex(), first, last);
            m_list->append(element);
            endInsertRows();
        }
    
        void startAddingMoreElements()
        {
            QTimer::singleShot(1000, this, SLOT(addMoreElements()));
        }
    
    private slots:
    
        void addMoreElements()
        {
            append(qrand() % 100);
            startAddingMoreElements();
        }
    };
    
    
    int main(int argc, char *argv[])
    {
        QApplication a(argc, argv);
    
        QList<int> list;
        list << 1 << 10 << 34 << 111;
        ListBackedModel model(&list);
    
        QListView listView;
        listView.setModel(&model);
        listView.show();
    
        model.startAddingMoreElements();
    
        return a.exec();
    }
    
    #include "main.moc"