天天看點

QTreeView使用總結15,自定義model,支援item可編輯1,簡介2,效果3,代碼4,源碼

1,簡介

之前釋出的兩篇自定義model的文章,有小夥伴下載下傳源碼後發現元素不能編輯。

确實是的,因為我自己都是用來展示資料,沒做這個。

這篇文章實作item編輯功能。

2,效果

QTreeView使用總結15,自定義model,支援item可編輯1,簡介2,效果3,代碼4,源碼

但是由于我這個示例,真實資料隻有名稱、三門課成績,後面的展示資料都是根據這些實時計算出來的。

是以隻有真實資料支援修改,而且修改後 其他推算型資料也會自動重新整理。

這點需要注意。

3,代碼

主要需處理下面幾個地方:

1,QTreeView 也要設定編輯操作類型:

ui->treeView->setEditTriggers(QTreeView::DoubleClicked);			//單元格輕按兩下編輯
           

2,元素的 flags 要加可編輯屬性: Qt::ItemIsEditable

Qt::ItemFlags TreeModel::flags(const QModelIndex &index) const
{
    if (!index.isValid())
        return 0;

    //節點是否允許編輯
    Qt::ItemFlags flags = QAbstractItemModel::flags(index);
    flags |= Qt::ItemIsEditable;
    
    return flags;
}
           

3,另外data 函數裡,也需要對 Qt::EditRole 處理下,否則打開編輯框時,預設是空白。

這裡我們讓編輯框預設就顯示 item 的文本。

QVariant TreeModel::data(const QModelIndex &index, int role) const
{
    if (!index.isValid())
        return QVariant();

    TreeItem *item = static_cast<TreeItem*>(index.internalPointer());
    if (role == Qt::DisplayRole)
    {
        return item->data(index.column());
    }
    else if (role == Qt::EditRole)
    {
        //元素打開編輯框時,顯示的内容,如果沒有這行,編輯框出現時預設為空白
        return item->data(index.column());
    }
    else if( role == Qt::TextAlignmentRole )
    {
        if( index.column() == 0 )
        {
            //第1列左對齊
            return QVariant(Qt::AlignVCenter | Qt::AlignLeft);
        }
        else if( index.column() > 0 && index.column() < 6 )
        {
            //第2~6列右對齊
            return QVariant(Qt::AlignVCenter | Qt::AlignRight);
        }
        else
        {
            //其他列居中對齊
            return QVariant(Qt::AlignCenter);
        }
    }
    else if(role == Qt::TextColorRole)
    {
        if(index.column() == 6)
        {
            QString str = item->data(6).toString();
            if(str == QStringLiteral("不合格"))
            {
                //第7列(是否合格)如果不合格就設文本為紅色
                return QVariant(QColor("#FF0000"));
            }
        }
        return QVariant();
    }
    return QVariant();
}
           

4,setData 函數,就是編輯框輸入完後,應用時走的邏輯,我們去修改真實資料:

bool TreeModel::setData(const QModelIndex &index, const QVariant &value, int role)
{
    if (index.isValid() && role == Qt::EditRole)
    {
        TreeItem *item = static_cast<TreeItem*>(index.internalPointer());
        item->setData(index.column(), value);

        emit dataChanged(index, index);
        return true;
    }
    return false;
}
           

其中調用TreeItem 進行真正的修改:

可以看到真實資料隻有這幾個,是以也隻能修改這幾個資料。其他資料會在顯示時自動計算的。

void TreeItem::setData(int column, QVariant value)
{
    if(mLevel == 1)
    {
        //一級節點,班級
        if(column == 0)
        {
            CLASS* c = (CLASS*)mPtr;
            c->name = value.toString();
        }
    }
    else if(mLevel==2)
    {
        //二級節點學生資訊
        STUDENT* s = (STUDENT*)mPtr;
        switch (column)
        {
        case 0: s->name = value.toString();break;
        case 1: s->score1 = value.toInt();break;
        case 2: s->score2 = value.toInt();break;
        case 3: s->score3 = value.toInt();break;

        default:
            return ;
        }
    }
}
           

4,源碼

寫作不易,源碼有償提供:(注意連結是全套專欄完整源碼,請勿重複下載下傳)

https://mianbaoduo.com/o/bread/YZuTk5dx

歡迎入群交流:

群号碼:1149411109 (若滿加2群:917341904)

群名稱:Qt實戰派學習群

繼續閱讀