Hallo alle zusammen.
Ich erstelle ein QSqlRelationalTableModel und liefere es an eine QTableView.
Alles funktioniert wunderbar (Relations werden mit Combos angezeigt)
Nun wollte ich auch mittels QSqlRelationalTableModel eine Suche und Filterung einbauen ( Funktioniert auch wunderbar) nur verschwindet die ComboBox bei den Related Einträgen der Inhalt wird jedoch aus der Relation übernommen.
Mit anderen Worten:
Ist es möglich einer QTableView ein QSortFilterProxyModel zuzuweisen (um Filtern und Suchen zu können) bei gleichzeitiger Verwendung eines QSqlRelationalTableModel???
Ich habe mich auch ein wenig schlau gemacht und folgendes gefunden:
mapFromSource
Liege ich da richtig oder bin ich damit auf dem Holzweg?
Bin begeisteter jedoch blutiger Anfänger und wäre für jede Hilfe dankbar.
QSortFilterProxyModel und QSqlRelationalTableModel
-
pfusterschmied
- Beiträge: 91
- Registriert: 14. Mai 2007 11:19
- Wohnort: Salzburg
- Kontaktdaten:
-
pfusterschmied
- Beiträge: 91
- Registriert: 14. Mai 2007 11:19
- Wohnort: Salzburg
- Kontaktdaten:
Nach langer Zeit endlich eine Lösung!
Hi Leute,
da keiner mir helfen konnte, wollte habe ich meinen zwei Gehirnhelften zusammen gelegt und eine Lösung gefunden. Programmiertechnisch ist es nicht das Optimum aber es funktioniert. Vielleicht kann ich damit den einen oder anderen helfen.
Auf der Grundlage dieses Foreneintrags: http://www.qtforum.de/forum/viewtopic.php?p=3893& und dem nachstehende Code ist es möglich ein QSqlRelationalTableModel mit QSortFilterProxyModel zu filtern und in einer einer QTableView anzeigen zu lassen. Dabei können trotzt des QSortFilterProxyModel die Relations in der DB in der QTableView mittels QComboBox genutzt werden.
da keiner mir helfen konnte, wollte habe ich meinen zwei Gehirnhelften zusammen gelegt und eine Lösung gefunden. Programmiertechnisch ist es nicht das Optimum aber es funktioniert. Vielleicht kann ich damit den einen oder anderen helfen.
Auf der Grundlage dieses Foreneintrags: http://www.qtforum.de/forum/viewtopic.php?p=3893& und dem nachstehende Code ist es möglich ein QSqlRelationalTableModel mit QSortFilterProxyModel zu filtern und in einer einer QTableView anzeigen zu lassen. Dabei können trotzt des QSortFilterProxyModel die Relations in der DB in der QTableView mittels QComboBox genutzt werden.
Code: Alles auswählen
// tableView.cpp
#include "tableview.h"
#include "myProxyModel.h"
#include "delegate.h"
tableModel::tableModel()
{
// Relational Table Model definieren
personModel = new QSqlRelationalTableModel(this);
personModel->setTable("yourTable");
personModel->setEditStrategy(QSqlTableModel::OnManualSubmit);
personModel->setRelation(3,QSqlRelation("yourRelation","uid", "sf"));
personModel->setRelation(4,QSqlRelation("yourRelation","uid", "epterm"));
personModel->setRelation(5,QSqlRelation("yourRelation","uid", "status"));
personModel->select();
// Kopfzeilen definieren
personModel->setHeaderData(0, Qt::Horizontal, QObject::trUtf8("Uid"));
personModel->setHeaderData(1, Qt::Horizontal, QObject::trUtf8("Vorname"));
personModel->setHeaderData(2, Qt::Horizontal, QObject::trUtf8("Nachname"));
//Filter Model
proxyModel = new MySortFilterProxyModel;
proxyModel->setDynamicSortFilter(true);
proxyModel->setSourceModel(personModel);
proxyModel->sort(2, Qt::AscendingOrder);
// Tabelle füllen
personTableView->setModel(personModel);
personTableView->setItemDelegate(new QSqlRelationalDelegate(this));
personTableView->setSortingEnabled(TRUE);
personTableView->setAlternatingRowColors(TRUE);
personTableView->sortByColumn ( 2,Qt::AscendingOrder);
personTableView->setSelectionMode(QAbstractItemView::SingleSelection);
personTableView->setSelectionBehavior(QAbstractItemView::SelectRows);
// Delegate inizialisieren
delegate = new ComboBoxDelegate ;
Code: Alles auswählen
//myProxyModel.cpp
#include "myProxyModel.h"
MySortFilterProxyModel::MySortFilterProxyModel(QObject *parent)
: QSortFilterProxyModel(parent)
{
}
bool MySortFilterProxyModel::filterAcceptsRow(int sourceRow,
const QModelIndex &sourceParent) const
{
QModelIndex index0 = sourceModel()->index(sourceRow, 0, sourceParent);
QModelIndex index1 = sourceModel()->index(sourceRow, 1, sourceParent);
QModelIndex index2 = sourceModel()->index(sourceRow, 2, sourceParent);
QModelIndex index3 = sourceModel()->index(sourceRow, 3, sourceParent);
QModelIndex index4 = sourceModel()->index(sourceRow, 4, sourceParent);
QModelIndex index5 = sourceModel()->index(sourceRow, 5, sourceParent);
return (sourceModel()->data(index0).toString().contains(filterRegExp())
|| sourceModel()->data(index1).toString().contains(filterRegExp())
|| sourceModel()->data(index2).toString().contains(filterRegExp())
|| sourceModel()->data(index3).toString().contains(filterRegExp())
|| sourceModel()->data(index4).toString().contains(filterRegExp())
|| sourceModel()->data(index5).toString().contains(filterRegExp()) );
}
}
Code: Alles auswählen
//delegate.cpp
#include "delegate.h"
ComboBoxDelegate::ComboBoxDelegate( QObject *parent )
: QItemDelegate( parent ) {}
QWidget *ComboBoxDelegate::createEditor( QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index ) const
{
if ( index.column() == 3 )
{
QComboBox *combo = new QComboBox( parent );
// EP Term Combos füllen
QSqlQuery myEPTermQuery;
QStringList EPTermCombo;
myEPTermQuery.exec("SELECT * FROM `your_relation`");
while (myEPTermQuery.next())
{
if (myEPTermQuery.value(1) != "Fehler")
{
EPTermCombo += myEPTermQuery.value(1).toString();
}
}
combo->addItems(EPTermCombo);
//Connect nach außen
connect( combo, SIGNAL( activated( int ) ), this, SLOT( emitCommitData() ) );
return combo;
}
else if ( index.column() == 4 )
{
QComboBox *combo = new QComboBox( parent );
// EP Term Combos füllen
QSqlQuery myEPTermQuery;
QStringList EPTermCombo;
myEPTermQuery.exec("SELECT * FROM `your_relation`");
while (myEPTermQuery.next())
{
if (myEPTermQuery.value(1) != "Fehler")
{
EPTermCombo += myEPTermQuery.value(1).toString();
}
}
combo->addItems(EPTermCombo);
//Connect nach außen
connect( combo, SIGNAL( activated( int ) ), this, SLOT( emitCommitData() ) );
return combo;
}
else if ( index.column() == 5 )
{
QComboBox *combo = new QComboBox( parent );
// EP Term Combos füllen
QSqlQuery myEPTermQuery;
QStringList EPTermCombo;
myEPTermQuery.exec("SELECT * FROM `your_relation`");
while (myEPTermQuery.next())
{
if (myEPTermQuery.value(1) != "Fehler")
{
EPTermCombo += myEPTermQuery.value(1).toString();
}
}
combo->addItems(EPTermCombo);
//Connect nach außen
connect( combo, SIGNAL( activated( int ) ), this, SLOT( emitCommitData() ) );
return combo;
} else
return QItemDelegate::createEditor( parent, option, index ); // Extrem wichtig, sonst kommt man nicht mehr zurück.
}
void ComboBoxDelegate::setEditorData( QWidget *editor, const QModelIndex &index ) const
{
QComboBox *combo = qobject_cast<QComboBox *>( editor );
if ( !combo )
{
QItemDelegate::setEditorData( editor, index ); // Extrem wichtig, sonst kommt man nicht mehr zurück.
return;
}
//int pos = combo -> findText(index.model()->data(index).toString(), Qt::MatchExactly);
//qDebug() << index.model()->data(index).toString();
//combo -> setCurrentIndex( pos );
}
void ComboBoxDelegate::setModelData( QWidget *editor, QAbstractItemModel *model, const QModelIndex &index ) const
{
QComboBox *combo = qobject_cast<QComboBox *>( editor );
if ( !combo )
{
QItemDelegate::setModelData( editor, model, index ); // Extrem wichtig, sonst kommt man nicht mehr zurück.
return;
}
int auswahl = combo ->currentIndex() + 1;
model -> setData( index, auswahl );
}
void ComboBoxDelegate::emitCommitData()
{
emit commitData( qobject_cast<QWidget *>( sender() ) );
}