在QListView上使用QStyledItemDelegate和QSqlQueryModel

时间:2011-03-17 03:34:26

标签: qt qt4 symbian

我有一个QListView,它将QSqlQueryModel设置为其模型。如何使用QStyledItemDelegate来自定义QListView的行的外观(例如显示2个文本行)?

QSqlDatabase db = QSqlDatabase::addDatabase( "QSQLITE" );
db.setDatabaseName( "test.db" );
if( !db.open() )
{
    qDebug() << db.lastError();
    qFatal( "Failed to connect." );
}

qDebug( "Connected!" );

QSqlQueryModel *sqlModel = new QSqlQueryModel;
sqlModel->setQuery("SELECT * FROM entries");

mListWidget->setModel(sqlModel);

基本上,我认为我需要做的是以某种方式“匹配”角色到db表的字段,以便能够从QStyledItemDelegate获取数据,使用类似这样的东西:

void ListViewDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
    [...]
    QString headerText = qvariant_cast<QString>(index.data(headerRole));
    QString subText = qvariant_cast<QString>(index.data(subHeaderRole));
    [...]
}

谢谢!

1 个答案:

答案 0 :(得分:15)

您当然可以使用QStyledItemDelegate进行自定义项目绘制。 QModelIndex具有对模型对象的引用,您可以使用它来获取“条目”记录字段。如果需要显示更多数据,则需要重新定义模型的sizeHint方法以增加项目大小。除此之外,它或多或少是微不足道的。

请参阅下面的示例是否适用于您:

class ListViewDelegate : public QStyledItemDelegate
{
protected:
    void paint(QPainter* painter, const QStyleOptionViewItem& option, const QModelIndex& index) const
    {
        QStyleOptionViewItemV4 opt = option;
        initStyleOption(&opt, index);

        QString line0 = index.model()->data(index.model()->index(index.row(), 1)).toString();
        QString line1 = index.model()->data(index.model()->index(index.row(), 2)).toString();

        // draw correct background
        opt.text = "";
        QStyle *style = opt.widget ? opt.widget->style() : QApplication::style();
        style->drawControl(QStyle::CE_ItemViewItem, &opt, painter, opt.widget);

        QRect rect = opt.rect;
        QPalette::ColorGroup cg = opt.state & QStyle::State_Enabled ? QPalette::Normal : QPalette::Disabled;
        if (cg == QPalette::Normal && !(opt.state & QStyle::State_Active))
            cg = QPalette::Inactive;

        // set pen color
        if (opt.state & QStyle::State_Selected)
            painter->setPen(opt.palette.color(cg, QPalette::HighlightedText));
        else
            painter->setPen(opt.palette.color(cg, QPalette::Text));

        // draw 2 lines of text
        painter->drawText(QRect(rect.left(), rect.top(), rect.width(), rect.height()/2),
                          opt.displayAlignment, line0);
        painter->drawText(QRect(rect.left(), rect.top()+rect.height()/2, rect.width(), rect.height()/2),
                          opt.displayAlignment, line1);
    }

    QSize sizeHint(const QStyleOptionViewItem & option, const QModelIndex & index ) const
    {
        QSize result = QStyledItemDelegate::sizeHint(option, index);
        result.setHeight(result.height()*2);
        return result;
    }
};

测试数据库集在此处定义:

QSqlError initDb()
{
    QSqlDatabase db = QSqlDatabase::addDatabase("QSQLITE");
    db.setDatabaseName(":memory:");

    if (!db.open())
        return db.lastError();

    QStringList tables = db.tables();
    if (tables.contains("test", Qt::CaseInsensitive))
        return QSqlError();

    QSqlQuery q;
    if (!q.exec(QLatin1String("create table entries(id integer primary key, first_line varchar, second_line varchar)")))
        return q.lastError();

    q.exec("insert into entries(id, first_line, second_line) values(0, 'first line 0', 'second line 0')");
    q.exec("insert into entries(id, first_line, second_line) values(1, 'first line 1', 'second line 1')");
    q.exec("insert into entries(id, first_line, second_line) values(2, 'first line 2', 'second line 2')");

    return QSqlError();
}

模型和列表视图定义:

initDb();

QSqlQueryModel *sqlModel = new QSqlQueryModel();
sqlModel->setQuery("SELECT * FROM entries");

ui->listView->setModel(sqlModel);
ui->listView->setItemDelegate(new ListViewDelegate());

希望这有帮助,尊重