QSortFilterProxyModel und QSqlRelationalTableModel

Alles rund um die Programmierung mit Qt
Antworten
pfusterschmied
Beiträge: 91
Registriert: 14. Mai 2007 11:19
Wohnort: Salzburg
Kontaktdaten:

QSortFilterProxyModel und QSqlRelationalTableModel

Beitrag von pfusterschmied »

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.
pfusterschmied
Beiträge: 91
Registriert: 14. Mai 2007 11:19
Wohnort: Salzburg
Kontaktdaten:

Nach langer Zeit endlich eine Lösung!

Beitrag von pfusterschmied »

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.

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() ) ); 
}

Antworten