/**************************************************************************** ** ** Copyright (C) 2005-2008 Trolltech ASA. All rights reserved. ** ** This file is part of the example classes of the Qt Toolkit. ** ** This file may be used under the terms of the GNU General Public ** License versions 2.0 or 3.0 as published by the Free Software ** Foundation and appearing in the files LICENSE.GPL2 and LICENSE.GPL3 ** included in the packaging of this file. Alternatively you may (at ** your option) use any later version of the GNU General Public ** License if such license has been publicly approved by Trolltech ASA ** (or its successors, if any) and the KDE Free Qt Foundation. In ** addition, as a special exception, Trolltech gives you certain ** additional rights. These rights are described in the Trolltech GPL ** Exception version 1.2, which can be found at ** http://www.trolltech.com/products/qt/gplexception/ and in the file ** GPL_EXCEPTION.txt in this package. ** ** Please review the following information to ensure GNU General ** Public Licensing requirements will be met: ** http://trolltech.com/products/qt/licenses/licensing/opensource/. If ** you are unsure which license is appropriate for your use, please ** review the following information: ** http://trolltech.com/products/qt/licenses/licensing/licensingoverview ** or contact the sales department at sales@trolltech.com. ** ** In addition, as a special exception, Trolltech, as the sole ** copyright holder for Qt Designer, grants users of the Qt/Eclipse ** Integration plug-in the right for the Qt/Eclipse Integration to ** link to functionality provided by Qt Designer and its related ** libraries. ** ** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, ** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR ** A PARTICULAR PURPOSE. Trolltech reserves all rights not expressly ** granted herein. ** ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. ** ****************************************************************************/ #include <QtGui> #include "variantdelegate.h" VariantDelegate::VariantDelegate(QObject *parent) : QItemDelegate(parent) { boolExp.setPattern("true|false"); boolExp.setCaseSensitivity(Qt::CaseInsensitive); byteArrayExp.setPattern("[\\x00-\\xff]*"); charExp.setPattern("."); colorExp.setPattern("\\(([0-9]*),([0-9]*),([0-9]*),([0-9]*)\\)"); doubleExp.setPattern(""); pointExp.setPattern("\\((-?[0-9]*),(-?[0-9]*)\\)"); rectExp.setPattern("\\((-?[0-9]*),(-?[0-9]*),(-?[0-9]*),(-?[0-9]*)\\)"); signedIntegerExp.setPattern("-?[0-9]*"); sizeExp = pointExp; unsignedIntegerExp.setPattern("[0-9]*"); dateExp.setPattern("([0-9]{,4})-([0-9]{,2})-([0-9]{,2})"); timeExp.setPattern("([0-9]{,2}):([0-9]{,2}):([0-9]{,2})"); dateTimeExp.setPattern(dateExp.pattern() + "T" + timeExp.pattern()); } void VariantDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const { if (index.column() == 2) { QVariant value = index.model()->data(index, Qt::UserRole); if (!isSupportedType(value.type())) { QStyleOptionViewItem myOption = option; myOption.state &= ~QStyle::State_Enabled; QItemDelegate::paint(painter, myOption, index); return; } } QItemDelegate::paint(painter, option, index); } QWidget *VariantDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem & /* option */, const QModelIndex &index) const { if (index.column() != 2) return 0; QVariant originalValue = index.model()->data(index, Qt::UserRole); if (!isSupportedType(originalValue.type())) return 0; QLineEdit *lineEdit = new QLineEdit(parent); lineEdit->setFrame(false); QRegExp regExp; switch (originalValue.type()) { case QVariant::Bool: regExp = boolExp; break; case QVariant::ByteArray: regExp = byteArrayExp; break; case QVariant::Char: regExp = charExp; break; case QVariant::Color: regExp = colorExp; break; case QVariant::Date: regExp = dateExp; break; case QVariant::DateTime: regExp = dateTimeExp; break; case QVariant::Double: regExp = doubleExp; break; case QVariant::Int: case QVariant::LongLong: regExp = signedIntegerExp; break; case QVariant::Point: regExp = pointExp; break; case QVariant::Rect: regExp = rectExp; break; case QVariant::Size: regExp = sizeExp; break; case QVariant::Time: regExp = timeExp; break; case QVariant::UInt: case QVariant::ULongLong: regExp = unsignedIntegerExp; break; default: ; } if (!regExp.isEmpty()) { QValidator *validator = new QRegExpValidator(regExp, lineEdit); lineEdit->setValidator(validator); } return lineEdit; } void VariantDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const { QVariant value = index.model()->data(index, Qt::UserRole); if (QLineEdit *lineEdit = qobject_cast<QLineEdit *>(editor)) lineEdit->setText(displayText(value)); } void VariantDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const { QLineEdit *lineEdit = qobject_cast<QLineEdit *>(editor); if (!lineEdit->isModified()) return; QString text = lineEdit->text(); const QValidator *validator = lineEdit->validator(); if (validator) { int pos; if (validator->validate(text, pos) != QValidator::Acceptable) return; } QVariant originalValue = index.model()->data(index, Qt::UserRole); QVariant value; switch (originalValue.type()) { case QVariant::Char: value = text.at(0); break; case QVariant::Color: colorExp.exactMatch(text); value = QColor(qMin(colorExp.cap(1).toInt(), 255), qMin(colorExp.cap(2).toInt(), 255), qMin(colorExp.cap(3).toInt(), 255), qMin(colorExp.cap(4).toInt(), 255)); break; case QVariant::Date: { QDate date = QDate::fromString(text, Qt::ISODate); if (!date.isValid()) return; value = date; } break; case QVariant::DateTime: { QDateTime dateTime = QDateTime::fromString(text, Qt::ISODate); if (!dateTime.isValid()) return; value = dateTime; } break; case QVariant::Point: pointExp.exactMatch(text); value = QPoint(pointExp.cap(1).toInt(), pointExp.cap(2).toInt()); break; case QVariant::Rect: rectExp.exactMatch(text); value = QRect(rectExp.cap(1).toInt(), rectExp.cap(2).toInt(), rectExp.cap(3).toInt(), rectExp.cap(4).toInt()); break; case QVariant::Size: sizeExp.exactMatch(text); value = QSize(sizeExp.cap(1).toInt(), sizeExp.cap(2).toInt()); break; case QVariant::StringList: value = text.split(","); break; case QVariant::Time: { QTime time = QTime::fromString(text, Qt::ISODate); if (!time.isValid()) return; value = time; } break; default: value = text; value.convert(originalValue.type()); } model->setData(index, displayText(value), Qt::DisplayRole); model->setData(index, value, Qt::UserRole); } bool VariantDelegate::isSupportedType(QVariant::Type type) { switch (type) { case QVariant::Bool: case QVariant::ByteArray: case QVariant::Char: case QVariant::Color: case QVariant::Date: case QVariant::DateTime: case QVariant::Double: case QVariant::Int: case QVariant::LongLong: case QVariant::Point: case QVariant::Rect: case QVariant::Size: case QVariant::String: case QVariant::StringList: case QVariant::Time: case QVariant::UInt: case QVariant::ULongLong: return true; default: return false; } } QString VariantDelegate::displayText(const QVariant &value) { switch (value.type()) { case QVariant::Bool: case QVariant::ByteArray: case QVariant::Char: case QVariant::Double: case QVariant::Int: case QVariant::LongLong: case QVariant::String: case QVariant::UInt: case QVariant::ULongLong: return value.toString(); case QVariant::Color: { QColor color = qvariant_cast<QColor>(value); return QString("(%1,%2,%3,%4)") .arg(color.red()).arg(color.green()) .arg(color.blue()).arg(color.alpha()); } case QVariant::Date: return value.toDate().toString(Qt::ISODate); case QVariant::DateTime: return value.toDateTime().toString(Qt::ISODate); case QVariant::Invalid: return "<Invalid>"; case QVariant::Point: { QPoint point = value.toPoint(); return QString("(%1,%2)").arg(point.x()).arg(point.y()); } case QVariant::Rect: { QRect rect = value.toRect(); return QString("(%1,%2,%3,%4)") .arg(rect.x()).arg(rect.y()) .arg(rect.width()).arg(rect.height()); } case QVariant::Size: { QSize size = value.toSize(); return QString("(%1,%2)").arg(size.width()).arg(size.height()); } case QVariant::StringList: return value.toStringList().join(","); case QVariant::Time: return value.toTime().toString(Qt::ISODate); default: break; } return QString("<%1>").arg(value.typeName()); }