基于QItemDelegate的例子2 trackeEditorDelegate
?trackeEditorDelegate例子是《#include <QApplication>#include "trackeditor.h"int main(int argc, char *argv[]){ QApplication app(argc, argv); QList<Track> tracks; tracks << Track("The Flying Dutchman: Overture", 630) << Track("The Flying Dutchman: Wie aus der Fern laengst " "vergangner Zeiten", 374) << Track("The Flying Dutchman: Steuermann, lass die Wacht", 152) << Track("Die Walkuere: Ride of the Valkyries", 286) << Track("Tannhaeuser: Freudig begruessen wir die edle " "Halle", 384) << Track("Tannhaeuser: Wie Todesahnung - O du mein holder " "Abendstern", 257) << Track("Lohengrin: Treulich gefuert ziehet dahnin", 294) << Track("Lohengrin: In fernem Land", 383) << Track("Die Meistersinger von Nuernberg: Overture", 543) << Track("Die Meistersinger von Nuernberg: Verachtet mir " "die Meister nicht", 200) << Track("Die Meistersinger von Nuernberg: Ehrt eure " "deutschen Meister", 112) << Track("Goetterdaemmerung: Funeral Music", 469) << Track("Tristan und Isolde: Mild und leise, wie er " "laechelt", 375); //自定义编辑控件 TrackEditor editor(&tracks); editor.resize(600, 300); editor.show(); return app.exec();}
?
?TrackEditor.h
?
#ifndef TRACKEDITOR_H#define TRACKEDITOR_H#include <QDialog>#include <QList>class QDialogButtonBox;class QTableWidget;class Track{public: Track(const QString &title = "", int duration = 0); QString title; int duration;};class TrackEditor : public QDialog{ Q_OBJECTpublic: TrackEditor(QList<Track> *tracks, QWidget *parent = 0); void done(int result);private slots: void addTrack();private: QTableWidget *tableWidget; QDialogButtonBox *buttonBox; QList<Track> *tracks;};#endif?
TrackEditor.cpp
?
#include <QtGui>#include "trackdelegate.h"#include "trackeditor.h"Track::Track(const QString &title, int duration){ this->title = title; this->duration = duration;}TrackEditor::TrackEditor(QList<Track> *tracks, QWidget *parent) : QDialog(parent){ this->tracks = tracks; //视图控件 tableWidget = new QTableWidget(tracks->count(), 2); //设置委托 tableWidget->setItemDelegate(new TrackDelegate(1)); //设置视图列头 tableWidget->setHorizontalHeaderLabels( QStringList() << tr("Track") << tr("Duration")); //初始化视图内容 for (int row = 0; row < tracks->count(); ++row) { Track track = tracks->at(row); QTableWidgetItem *item0 = new QTableWidgetItem(track.title); //设置第0列中所有项 tableWidget->setItem(row, 0, item0); QTableWidgetItem *item1 = new QTableWidgetItem(QString::number(track.duration)); item1->setTextAlignment(Qt::AlignRight); //设置第1列所有项 tableWidget->setItem(row, 1, item1); } //根据委托的SizeHint,重新设置视图大小 tableWidget->resizeColumnToContents(0); buttonBox = new QDialogButtonBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel); QPushButton *addTrackButton = buttonBox->addButton(tr("&Add Track"), QDialogButtonBox::ActionRole); connect(addTrackButton, SIGNAL(clicked()), this, SLOT(addTrack())); connect(buttonBox, SIGNAL(accepted()), this, SLOT(accept())); connect(buttonBox, SIGNAL(rejected()), this, SLOT(reject())); QVBoxLayout *mainLayout = new QVBoxLayout; mainLayout->addWidget(tableWidget); mainLayout->addWidget(buttonBox); setLayout(mainLayout); setWindowTitle(tr("Track Editor"));}void TrackEditor::done(int result){ //ok if (result == QDialog::Accepted) { tracks->clear(); for (int row = 0; row < tableWidget->rowCount(); ++row) { QString title = tableWidget->item(row, 0)->text(); QTableWidgetItem *item = tableWidget->item(row, 1); int duration = item ? item->text().toInt() : 0; tracks->append(Track(title, duration)); } } QDialog::done(result);}void TrackEditor::addTrack(){ //在最后新插入一行 tableWidget->insertRow(tableWidget->rowCount());}?
TrackDelegate.h
?
#ifndef TRACKDELEGATE_H#define TRACKDELEGATE_H#include <QItemDelegate>class TrackDelegate : public QItemDelegate{ Q_OBJECTpublic: TrackDelegate(int durationColumn, QObject *parent = 0); //重新绘制 void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const; QWidget *createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const; void setEditorData(QWidget *editor, const QModelIndex &index) const; void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const;private slots: void commitAndCloseEditor();private: int durationColumn;};#endif?TrackDelegate.cpp
?
#include <QtGui>#include "trackdelegate.h"TrackDelegate::TrackDelegate(int durationColumn, QObject *parent) : QItemDelegate(parent){ this->durationColumn = durationColumn;}void TrackDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const{ //保存音轨的列 if (index.column() == durationColumn) { //获得索引对应Model中的数据 int secs = index.model()->data(index, Qt::DisplayRole).toInt(); //设置时间格式字符串 分:秒 QString text = QString("%1:%2") .arg(secs / 60, 2, 10, QChar('0')) .arg(secs % 60, 2, 10, QChar('0')); //获取项风格设置 QStyleOptionViewItem myOption = option; myOption.displayAlignment = Qt::AlignRight | Qt::AlignVCenter; //绘制文本 drawDisplay(painter, myOption, myOption.rect, text); //如果当前有焦点,就绘制一个焦点矩形,否则什么都不做 drawFocus(painter, myOption, myOption.rect); } else{ //否则默认 QItemDelegate::paint(painter, option, index); }}QWidget *TrackDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const{ //音轨时间列 if (index.column() == durationColumn) { //时间编辑控件 QTimeEdit *timeEdit = new QTimeEdit(parent); //时间编辑控件文本格式 timeEdit->setDisplayFormat("mm:ss"); //如果编辑结束,激活提交和关闭槽 connect(timeEdit, SIGNAL(editingFinished()), this, SLOT(commitAndCloseEditor())); return timeEdit; } else { //否则使用默认委托处理 return QItemDelegate::createEditor(parent, option, index); }}//设置控件值void TrackDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const{ //音轨时间列 if (index.column() == durationColumn) { //获得当前索引在Model中的值 int secs = index.model()->data(index, Qt::DisplayRole).toInt(); //设置时间控件的值 QTimeEdit *timeEdit = qobject_cast<QTimeEdit *>(editor); timeEdit->setTime(QTime(0, secs / 60, secs % 60)); } else { QItemDelegate::setEditorData(editor, index); }}//设置Model值void TrackDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const{ //音轨列 if (index.column() == durationColumn) { //获得时间控件值 QTimeEdit *timeEdit = qobject_cast<QTimeEdit *>(editor); QTime time = timeEdit->time(); int secs = (time.minute() * 60) + time.second(); //设置模型值 model->setData(index, secs); } else { //否则使用默认委托处理 QItemDelegate::setModelData(editor, model, index); }}//自定义 提交和关闭 槽函数void TrackDelegate::commitAndCloseEditor(){ QTimeEdit *editor = qobject_cast<QTimeEdit *>(sender()); //提交该控件的值 否则模型中数据不更改 emit commitData(editor); //关闭该控件 可以告知委托去代开下一个控件 emit closeEditor(editor);}