zoukankan      html  css  js  c++  java
  • QAbstractItemModel使用样例与解析(Model::index使用了createIndex,它会被销毁吗?被销毁了,因为栈对象出了括号就会被销毁)

    参考:qt源码
    qstandarditemmodel_p.h
    qstandarditemmodel.h
    qstandarditemmodel.cpp
    qabstractitemmodel.h
    qabstractitemmodel.cpp

    QAbstractItemModel是一个接口类,使用时需要从它继承下来,实现相关的函数后使用。
    不同于QStandardItemModel,使用QAbstractItemModel的话,需要自己构造树形结构数据,并在虚函数中返回对应的值。

    当然,简单使用的话,也可以快速构造出没有父节点的简单表格结构。
    形如根节点下列了几排几列子节点的表格情形。

    需要继承的类有:

    class HistoryModel : public QAbstractItemModel
    {
    public:
    explicit HistoryModel(QObject *parent = 0);

    // 构造父节点下子节点的索引
    virtual QModelIndex index(int row, int column, const QModelIndex &parent = QModelIndex()) const override;
    // 通过子节点索引获取父节点索引
    virtual QModelIndex parent(const QModelIndex &child) const override;
    // 获取父节点下子节点的行数
    virtual int rowCount(const QModelIndex &parent = QModelIndex()) const override;
    // 获取父节点下子节点列数
    virtual int columnCount(const QModelIndex &parent = QModelIndex()) const override;
    // 获取节点数据:包括DisplayRole|TextAlignmentRole等
    virtual QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override;
    };
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    实现几排几列表格情形的例子:

    HistoryModel::HistoryModel(QObject *parent /*= 0*/)
    : QAbstractItemModel(parent)
    {
    }

    QModelIndex HistoryModel::index(int row, int column, const QModelIndex &parent /*= QModelIndex()*/) const
    {
    // 创建普通索引
    return createIndex(row, column);
    }
    QModelIndex HistoryModel::parent(const QModelIndex &child) const
    {
    // 父节点均为跟节点
    return QModelIndex();
    }
    int HistoryModel::rowCount(const QModelIndex &parent /*= QModelIndex()*/) const
    {
    // 根节点下有5行,其它行下没有
    if (parent.row() == -1)
    {
    return 5;
    }
    return 0;
    }
    int HistoryModel::columnCount(const QModelIndex &parent /*= QModelIndex()*/) const
    {
    // 每行有量列
    return 2;
    }

    QVariant HistoryModel::data(const QModelIndex &index, int role /*= Qt::DisplayRole*/) const
    {
    // 节点内容:左对齐,显示行列号
    if (role == Qt::TextAlignmentRole)
    return int(Qt::AlignLeft | Qt::AlignVCenter);
    else if (role == Qt::DisplayRole)
    return QString("row=%1,col=%2").arg(index.row()).arg(index.column());
    else
    return QVariant();
    }
    进一步使用,添加树形结构,自己构造树形结构数据:

    struct NodeInfo
    {
    QModelIndex parent; // 父节点index
    QString sData; // 自身数据
    QVector<NodeInfo*> childNodes; // 子节点
    NodeInfo(QModelIndex parentIdx, QString s):parent(parentIdx), sData(s){}
    };
    1
    2
    3
    4
    5
    6
    7
    生成如下的这种界面:两个level=1节点,每个节点下有一些数据

    可以这样来做:
    每个节点存储一个NodeInfo信息,这样
    1. 每个节点可以查询子节点数量
    2. 每个节点可以查询到自身数据
    3. 可以根据NodeInfo信息(row/col/this)获取到QModeIndex
    4. 数据构造时,形成NodeInfo的树形层次
    5. QAbstractItemModel的接口中,index函数中绑定NodeInfo
    6. QAbstractItemModel的其它接口中,查询NodeInfo并使用

    HistoryModel::HistoryModel(QObject *parent /*= 0*/)
    : QAbstractItemModel(parent)
    {
    // 创建root节点
    m_pRootNode = new NodeInfo(nullptr, "rootNode", -1, -1);
    m_receiveInfo = new NodeInfo(m_pRootNode, "ReceiveMessage", 0, 0);
    m_replyInfo = new NodeInfo(m_pRootNode, "ReplyMessage", 1, 0);
    m_pRootNode->childNodes.append(m_receiveInfo);
    m_pRootNode->childNodes.append(m_replyInfo);
    }

    QModelIndex HistoryModel::index(int row, int column, const QModelIndex &parent /*= QModelIndex()*/) const
    {
    if (parent.row() == -1 && parent.column() == -1)
    {
    // 首层节点绑定关系
    if (row < m_pRootNode->childNodes.count())
    return createIndex(row, column, m_pRootNode->childNodes[row]);
    }
    else
    {
    // 其它层节点绑定关系
    if (parent.internalPointer() != nullptr)
    {
    NodeInfo* pNode = reinterpret_cast<NodeInfo*>(parent.internalPointer());
    if (pNode->childNodes.size() > row)
    {
    return createIndex(row, column, pNode->childNodes[row]);
    }
    }
    }
    return QModelIndex();
    }

    QModelIndex HistoryModel::parent(const QModelIndex &child) const
    {
    if (child.internalPointer() != nullptr)
    {
    NodeInfo* pNode = reinterpret_cast<NodeInfo*>(child.internalPointer());
    NodeInfo* pParent = pNode->parent;
    if (pParent != nullptr)
    {
    // 根据父节点信息:row/col/node*获取Index
    return createIndex(pParent->nRow, pParent->nCol, pParent);;
    }
    }
    return QModelIndex();
    }
    int HistoryModel::rowCount(const QModelIndex &parent) const
    {
    if (parent.internalPointer() == nullptr)
    {
    // 根节点下的数据行数
    return m_pRootNode->childNodes.count();
    }
    else
    {
    // 节点下的数据行数
    NodeInfo* pNode = reinterpret_cast<NodeInfo*>(parent.internalPointer());
    return pNode->childNodes.size();
    }
    }
    int HistoryModel::columnCount(const QModelIndex &parent /*= QModelIndex()*/) const
    {
    // 每行有量列
    return 1;
    }

    QVariant HistoryModel::data(const QModelIndex &index, int role /*= Qt::DisplayRole*/) const
    {
    // 节点内容:左对齐,显示行列号
    if (role == Qt::TextAlignmentRole)
    {
    return int(Qt::AlignLeft | Qt::AlignVCenter);
    }
    else if (role == Qt::DisplayRole)
    {
    if (index.internalPointer() == 0)
    {
    return QString("row=%1,col=%2").arg(index.row()).arg(index.column());
    }
    else
    {
    NodeInfo* pNode = reinterpret_cast<NodeInfo*>(index.internalPointer());
    return pNode->sData;
    }
    }
    else
    {
    return QVariant();
    }
    }
    (Owed by: 春夜喜雨 http://blog.csdn.net/chunyexiyu)
    ---------------------
    作者:春夜喜雨
    来源:CSDN
    原文:https://blog.csdn.net/chunyexiyu/article/details/77657624
    版权声明:本文为博主原创文章,转载请附上博文链接!

    void wokr()
    {
        QModelIndex index = model.getIndex();
        ...
        ...
        return;
       // 局部变量,函数退出时自动回收。
    }
    
    std::string func()
    {
    return "123";
    }
    你需要管返回值谁释放嘛?
    
    奇怪的问题
    
    std::string* func()
    {
    return new std::string("123");
    }
    但是这个你就要关心了
  • 相关阅读:
    2020.10.23 19级training 补题报告
    2020.10.17 天梯赛练习 补题报告
    2020.10.16 19级training 补题报告
    2020.10.9 19级training 补题报告
    2020.10.10 天梯赛练习 补题报告
    2020.10.3 天梯赛练习 补题报告
    2020.10.2 19级training 补题报告
    第十届山东省ACM省赛复现补题报告
    VVDI Key Tool Plus Adds VW Passat 2015 Key via OBD
    Xhorse VVDI Prog Software V5.0.3 Adds Many MCUs
  • 原文地址:https://www.cnblogs.com/findumars/p/11140057.html
Copyright © 2011-2022 走看看