Skip to content
Permalink
Browse files

[FEATURE] Honour the edit widgets settings also in attribute table.

git-svn-id: http://svn.osgeo.org/qgis/trunk/qgis@11150 c8812cc2-4d05-0410-92ff-de0c093fc19c
  • Loading branch information
wonder
wonder committed Jul 22, 2009
1 parent 36760eb commit 7d5df5d2f218a68a102ac36f19af66889b0075c5
@@ -15,38 +15,183 @@

#include <QItemDelegate>
#include <QLineEdit>
#include <QComboBox>
#include <QPainter>
#include <QCompleter>
#include <QSpinBox>
#include <QDoubleSpinBox>

#include "qgsattributetableview.h"
#include "qgsattributetablemodel.h"
#include "qgsattributetablefiltermodel.h"
#include "qgsattributetabledelegate.h"
#include "qgsvectordataprovider.h"
#include "qgsvectorlayer.h"
#include "qgsuniquevaluerenderer.h"
#include "qgssymbol.h"


QWidget * QgsAttributeTableDelegate::createEditor(
QWidget *parent,
const QStyleOptionViewItem &option,
const QModelIndex &index ) const
{
QWidget *editor = QItemDelegate::createEditor( parent, option, index );

QLineEdit *le = dynamic_cast<QLineEdit*>( editor );
if ( !le ) return editor;
QWidget *editor;

const QgsAttributeTableModel* m = dynamic_cast<const QgsAttributeTableModel*>( index.model() );
if ( !m ) return editor;
const QgsAttributeTableFilterModel* fm = dynamic_cast<const QgsAttributeTableFilterModel*>( index.model() );
if ( !fm )
{
return editor;
}
const QgsAttributeTableModel* m = dynamic_cast<const QgsAttributeTableModel*>( fm->sourceModel() );
if ( !m )
{
return editor;
}

int col = index.column();
QVariant::Type type = m->layer()->dataProvider()->fields()[col].type();
QgsVectorLayer::EditType editType = m->layer()->editType(col);

//need to created correct edit widget according to edit type of value
//and fill with data from correct source
if (editType == QgsVectorLayer::LineEdit ||
editType == QgsVectorLayer::UniqueValuesEditable ||
editType == QgsVectorLayer::FileName ||
editType == QgsVectorLayer::Immutable)
{ //these are all siple edits
editor = new QLineEdit(parent);
QLineEdit* le = dynamic_cast<QLineEdit*> ( editor );
le-> setReadOnly ( false );

if ( editType == QgsVectorLayer::UniqueValuesEditable )
{ //just this value has completer
QList<QVariant> values;
m->layer()->dataProvider()->uniqueValues( col, values );

QStringList svalues;
for ( QList<QVariant>::const_iterator it = values.begin(); it != values.end(); it++ )
svalues << it->toString();

QCompleter *c = new QCompleter( svalues );
c->setCompletionMode( QCompleter::PopupCompletion );
le->setCompleter( c );
}
if (editType == QgsVectorLayer::Immutable)
{
le->setReadOnly(true);
}
//validators if value needs it
if ( type == QVariant::Int )
{
le->setValidator( new QIntValidator( le ) );
}
else if ( type == QVariant::Double )
{
le->setValidator( new QDoubleValidator( le ) );
}
}
else if (editType == QgsVectorLayer::ValueMap)
{ //simple combobox from data from vector layer
editor = new QComboBox(parent);
QComboBox* cb = dynamic_cast<QComboBox*>( editor );
QMap<QString, QVariant> &map = m->layer()->valueMap(col);
QMap<QString, QVariant>::iterator it = map.begin();
for ( ; it != map.end(); it ++)
{
cb->addItem( it.key() ,it.value());
}
}
else if (editType == QgsVectorLayer::SliderRange)
{ //horizontal slider
editor = new QSlider(Qt::Horizontal, parent);
QSlider* s = dynamic_cast<QSlider*>(editor );
QgsVectorLayer::RangeData &range = m->layer()->range(col);
s->setMinimum( range.mMin.toInt() );
s->setMaximum( range.mMax.toInt() );
s->setPageStep( range.mStep.toInt() );
}
else if (editType == QgsVectorLayer::Classification)
{
// should be prepared probably to not change it always
int classificationField = -1;
QMap<QString, QString> classes;
const QgsUniqueValueRenderer *uvr = dynamic_cast<const QgsUniqueValueRenderer *>( m->layer()->renderer() );
if ( uvr )
{
classificationField = uvr->classificationField();
const QList<QgsSymbol *> symbols = uvr->symbols();

for ( int i = 0; i < symbols.size(); i++ )
{
QString label = symbols[i]->label();
QString name = symbols[i]->lowerValue();
if ( label == "" )
label = name;
classes.insert( name, label );
}
}
editor = new QComboBox(parent);
QComboBox* cb = dynamic_cast<QComboBox*>( editor );
for ( QMap<QString, QString>::const_iterator it = classes.begin(); it != classes.end(); it++ )
{
cb->addItem( it.value(), it.key() );
}
}
else if (editType == QgsVectorLayer::UniqueValues)
{
QList<QVariant> values;
m->layer()->dataProvider()->uniqueValues( col, values );

editor = new QComboBox(parent);
QComboBox* cb = dynamic_cast<QComboBox*>( editor );
cb->setEditable( true );

if ( type == QVariant::Int )
for ( QList<QVariant>::iterator it = values.begin(); it != values.end(); it++ )
cb->addItem( it->toString() );

}
else if (editType == QgsVectorLayer::Enumeration)
{
le->setValidator( new QIntValidator( le ) );
QStringList enumValues;
m->layer()->dataProvider()->enumValues( col, enumValues );

editor = new QComboBox(parent);
QComboBox* cb = dynamic_cast<QComboBox*>( editor );
QStringList::const_iterator s_it = enumValues.constBegin();
for ( ; s_it != enumValues.constEnd(); ++s_it )
{
cb->addItem( *s_it );
}
}
else if ( type == QVariant::Double )
else if (editType == QgsVectorLayer::EditRange)
{
le->setValidator( new QDoubleValidator( le ) );
if ( type == QVariant::Int )
{
int min = m->layer()->range( col ).mMin.toInt();
int max = m->layer()->range( col ).mMax.toInt();
int step = m->layer()->range( col ).mStep.toInt();
editor = new QSpinBox(parent);
QSpinBox* sb = dynamic_cast<QSpinBox*>( editor );

sb->setRange( min, max );
sb->setSingleStep( step );

}
else if ( type == QVariant::Double )
{
double min = m->layer()->range( col ).mMin.toDouble();
double max = m->layer()->range( col ).mMax.toDouble();
double step = m->layer()->range( col ).mStep.toDouble();
editor = new QDoubleSpinBox(parent);
QDoubleSpinBox* dsb = dynamic_cast<QDoubleSpinBox*>( editor );

dsb->setRange( min, max );
dsb->setSingleStep( step );
}
}


return editor;
}

@@ -68,3 +213,129 @@ void QgsAttributeTableDelegate::paint( QPainter * painter,
}
}


void QgsAttributeTableDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const
{


const QgsAttributeTableFilterModel* fm = dynamic_cast<const QgsAttributeTableFilterModel*>( index.model() );
if ( !fm )
{
return;
}
const QgsAttributeTableModel* m = dynamic_cast<const QgsAttributeTableModel*>( fm->sourceModel() );
if ( !m )
{
return;
}
int col = index.column();
QVariant::Type type = m->layer()->dataProvider()->fields()[col].type();
QgsVectorLayer::EditType editType = m->layer()->editType(col);
if (editType == QgsVectorLayer::LineEdit ||
editType == QgsVectorLayer::UniqueValuesEditable ||
editType == QgsVectorLayer::FileName ||
editType == QgsVectorLayer::Immutable)
{
QString qs = index.model()->data(index, Qt::DisplayRole).toString();

QLineEdit* le = dynamic_cast<QLineEdit*> ( editor );
le->setText( qs );
}
else if (editType == QgsVectorLayer::ValueMap ||
editType == QgsVectorLayer::Classification ||
editType == QgsVectorLayer::UniqueValues ||
editType == QgsVectorLayer::Enumeration)
{
QComboBox* cb = dynamic_cast<QComboBox*>( editor );
QVariant qs = index.model()->data(index, Qt::EditRole);
int cbIndex = cb->findData(qs);
if (cbIndex > -1)
{
cb->setCurrentIndex(cbIndex);
}
}
else if (editType == QgsVectorLayer::SliderRange)
{
int value = index.model()->data(index, Qt::EditRole).toInt();
QSlider* s = dynamic_cast<QSlider*>( editor );
s->setValue( value );
}
else if (editType == QgsVectorLayer::EditRange)
{
if ( type == QVariant::Int )
{
QSpinBox* sb = dynamic_cast<QSpinBox*>( editor );
int value = index.model()->data(index, Qt::EditRole).toInt();
sb->setValue( value );
}
else if ( type == QVariant::Double )
{
QDoubleSpinBox* sb = dynamic_cast<QDoubleSpinBox*>( editor );
double value = index.model()->data(index, Qt::EditRole).toDouble();
sb->setValue( value );
}
}
}



void QgsAttributeTableDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const
{
const QgsAttributeTableFilterModel* fm = dynamic_cast<const QgsAttributeTableFilterModel*>( index.model() );
if ( !fm )
{
return;
}
const QgsAttributeTableModel* m = dynamic_cast<const QgsAttributeTableModel*>( fm->sourceModel() );
if ( !m )
{
return;
}

int col = index.column();
QVariant::Type type = m->layer()->dataProvider()->fields()[col].type();
QgsVectorLayer::EditType editType = m->layer()->editType(col);
if (editType == QgsVectorLayer::LineEdit ||
editType == QgsVectorLayer::UniqueValuesEditable ||
editType == QgsVectorLayer::FileName ||
editType == QgsVectorLayer::Immutable)
{
QLineEdit* le = dynamic_cast<QLineEdit*> ( editor );
QString text = le->text();
QVariant value = QVariant (text);
model->setData( index, value );
}
else if (editType == QgsVectorLayer::ValueMap ||
editType == QgsVectorLayer::Classification ||
editType == QgsVectorLayer::UniqueValues ||
editType == QgsVectorLayer::Enumeration)
{
QComboBox* cb = dynamic_cast<QComboBox*>( editor );
model->setData(index, cb->itemData(cb->currentIndex()));
}
else if (editType == QgsVectorLayer::SliderRange)
{
QSlider* s = dynamic_cast<QSlider*>( editor );
model->setData( index, s->value() );
}
else if (editType == QgsVectorLayer::EditRange)
{
if ( type == QVariant::Int )
{
QSpinBox* sb = dynamic_cast<QSpinBox*>( editor );
model->setData( index, sb->value() );
}
else if ( type == QVariant::Double )
{
QDoubleSpinBox* sb = dynamic_cast<QDoubleSpinBox*>( editor );
model->setData( index, sb->value() );
}
}
}







@@ -17,6 +17,7 @@
#define QGSATTRIBUTETABLEDELEGATE_H

#include <QItemDelegate>
#include "qgsvectorlayer.h"
class QPainter;
/** \ingroup app
* A delegate item class for QgsAttributeTable (see Qt documentation for
@@ -43,6 +44,22 @@ class QgsAttributeTableDelegate : public QItemDelegate
QPainter * painter,
const QStyleOptionViewItem & option,
const QModelIndex & index ) const;

/**
* Sets data to editor widget. Overloads default metod
* @param editor editor which was created by create editor function in this class
* @param index index of field which is to be modified
*/
void setEditorData(QWidget *editor, const QModelIndex &index) const;

/**
* Sets data from editor backk to model. Overloads default metod
* @param editor editor which was created by create editor function in this class
* @param model model where data should be updated
* @param index index of field which is to be modified
*/
void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const;

};

#endif //QGSATTRIBUTETABLEDELEGATE_H
@@ -144,7 +144,7 @@ void QgsAttributeTableModel::layerModified( bool onlyGeometry )

loadLayer();
emit modelChanged();
emit headerDataChanged( Qt::Horizontal, 0, columnCount() );
emit headerDataChanged ( Qt::Horizontal, 0, columnCount() - 1);
}

void QgsAttributeTableModel::loadLayer()

0 comments on commit 7d5df5d

Please sign in to comment.
You can’t perform that action at this time.