[Qt-interest] Custom model and delegate for QComboBox
wim.delvaux at adaptiveplanet.com
wim.delvaux at adaptiveplanet.com
Thu Oct 29 00:16:25 CET 2009
I think you need to set the Delegate on the QDataWidgetMapper and not on the
combobox.
W
On Wednesday 28 October 2009 16:53:16 Wolfgang Pausch wrote:
> Hello,
>
> sorry for asking again. I´ve spent several hours trying to figure out
> where my mistake is, but I didn´t make it work yet :-(
>
> What do I have?
> - A QComboBox
> - A custom model for the QComboBox
> - A custom delegate implementing setEditorData for the QComboBox
> - Optionally a QDataWidgetMapper which maps the QComboBox and some other
> widgets. (the problem doesn´t disappear if I remove the QComboBox from the
> mapper).
>
> Am I right that those objects should interact in the following way:
> - The QComboBox has some items
> - Each of them corresponds to one QModelIndex in my QComboBox-internal
> custom model - The setEditorData method in my QComboBox-internal custom
> delegate should translate the values from the custom model into the values
> displayed by the QComboBox - The mapping enforced by the QDataWidgetMapper
> at each time only knows about the current item, mapping it to some
> QModelIndex entry of the model of the widget containing my QComboBox
>
> Problem:
> - I see the entries of my custom model 1:1 in the QComboBox, i.e. I see 1,
> 2, 3. - My custom delegates setEditorData would translate 1,2,3 into some
> human readable strings FOO, BAR, etc. - But it is not called, and I have no
> idea why not.
>
> What I could debug:
> - After setting the delegate, it actually is being set.
> - The only setEditorData methods in any *Delegate classes are called from
> my QDataWidgetMapper during toFirst(). - However, my problem doesn´t
> disappear if I remove my QComboBox from the mapper.
>
> Does anyone have some hint for me?
>
> Thanks,
>
> Wolfgang
>
> On Fri, 23 Oct 2009 15:03:50 +0200
>
> Wolfgang Pausch <wolfgang.pausch at uibk.ac.at> wrote:
> > Hello,
> >
> > I am trying to implement a custom model and a custom delegate for a
> > QComboBox. What I want to do is:
> >
> > - the model contains some codes loaded from a datamodel
> > - the delegate transforms them into human-readable strings
> >
> > However, my implementation so far simply doesn´t call setModelData. It
> > seems to ignore the delegate. Can anyone, based on the code snippets
> > below, give me a hint regarding what is my mistake? Especially: I don´t
> > want to edit anything in my ComboBox, just choose one of several choices.
> > Am I correct that I only need to overwrite setEditorData?
> >
> > Do I have to do something special in order to use this delegate? Do I
> > have to take care about the view? Is my assumption correct that once the
> > model is set, it should call the delegate itself, so I don´t have to call
> > some dataChanged signals etc. explicitely in the code below (e.g. in
> > addChoice)?
> >
> > I once became problems because I missed a const keyword when overwriting
> > some model method, but as far as I see, the signature of
> > ComboBoxDelegate::setEditorData is correct. Do you see any problem here?
> > (if this method would be called anything would be fine).
> >
> > Thanks,
> >
> > Wolfgang
> >
> > Where I set things up:
> >
> > QComboBox*
> > MitgliedAttributeWidgetFactory::constructMitgliedsartComboBox(DatabaseCon
> >text *databaseContext) { CodeManager *codeManager =
> > databaseContext->getCodeManager();
> >
> > ComboBoxModel *model = new ComboBoxModel();
> > model->addChoice(codeManager, "LANDESVERBAND_ORDENTLICH");
> > model->addChoice(codeManager, "LANDESVERBAND_AUSSERORDENTLICH");
> > model->addChoice(codeManager, "LANDESVERBAND_VEREINSMITGLIED");
> >
> > ComboBoxDelegate *delegate = new ComboBoxDelegate(databaseContext);
> >
> > QComboBox* mitgliedsartComboBox = new QComboBox();
> > mitgliedsartComboBox->setItemDelegate(delegate);
> > mitgliedsartComboBox->setModel(model);
> > return mitgliedsartComboBox;
> > }
> >
> > The model:
> >
> > class ComboBoxModel : public QAbstractListModel {
> >
> > public:
> > ComboBoxModel();
> > ~ComboBoxModel();
> >
> > void addChoice(CodeManager *codeManager, QString name);
> >
> > int rowCount(const QModelIndex &parent) const;
> > QVariant data(const QModelIndex &index, int role) const;
> >
> > private:
> > std::vector<CodeValue*> choices;
> >
> > };
> >
> > ComboBoxModel::ComboBoxModel() {
> > choices = std::vector<CodeValue*>();
> > }
> >
> > ComboBoxModel::~ComboBoxModel() {
> > for (std::vector<CodeValue*>::const_iterator it = choices.begin(); it !=
> > choices.end(); it++) { CodeValue* choice = *it;
> > delete choice;
> > }
> > }
> >
> > void ComboBoxModel::addChoice(CodeManager *codeManager, QString name) {
> > CodeValue* choice = codeManager->getCodeValueByName(name);
> > choices.push_back(choice);
> > }
> >
> > int ComboBoxModel::rowCount(const QModelIndex &parent) const {
> > return choices.size();
> > }
> >
> > QVariant ComboBoxModel::data(const QModelIndex &index, int role) const {
> > if (!index.isValid()) {
> > return QVariant();
> > }
> >
> > if (role == Qt::TextAlignmentRole) {
> > return int(Qt::AlignRight | Qt::AlignVCenter);
> > } else if (role == Qt::DisplayRole || role == Qt::EditRole) {
> > int row = index.row();
> > CodeValue *choice = choices[row];
> > int choiceId = choice->getId();
> > return QVariant(choiceId);
> > } else {
> > return QVariant();
> > }
> > }
> >
> >
> > The delegate:
> >
> > class ComboBoxDelegate : public QItemDelegate {
> > Q_OBJECT
> >
> > public:
> > ComboBoxDelegate(DatabaseContext *ndatabaseContext);
> > void setEditorData(QWidget *editor, const QModelIndex &index ) const;
> > void setModelData(QWidget *editor, QAbstractItemModel *model, const
> > QModelIndex &index ) const;
> >
> > private:
> > DatabaseContext *databaseContext;
> > };
> >
> > ComboBoxDelegate::ComboBoxDelegate(DatabaseContext *ndatabaseContext) {
> > databaseContext = ndatabaseContext;
> > }
> >
> > void ComboBoxDelegate::setEditorData(QWidget *editor, const QModelIndex
> > &index ) const { std::cout << "called setEditorData" << std::endl;
> >
> > QComboBox *comboBox = qobject_cast<QComboBox*>(editor);
> >
> > const QAbstractItemModel *model = index.model();
> > QVariant data = model->data(index, Qt::DisplayRole);
> > bool transformOk;
> > int codeBehindCombobox = data.toInt(&transformOk);
> >
> > if (comboBox == NULL) {
> > std::cerr << "ComboBoxDelegate::setEditorData says: comboBox is NULL.
> > Maybe this is a bug." << std::endl; } else if (!transformOk) {
> > std::cerr << "ComboBoxDelegate::setEditorData says: Value behind
> > comboBox is not an int. Maybe this is a bug." << std::endl; } else {
> > CodeManager *codeManager = databaseContext->getCodeManager();
> > CodeValue *codeValue =
> > codeManager->getCodeValueById(codeBehindCombobox);
> >
> > int row = index.row();
> > int column = index.column();
> > std::cout << "ComboBoxDelegate::setEditorData called for row " << row
> > << " and column " << column << std::endl;
> >
> > comboBox->setItemText(row, codeValue->getKurzText());
> > delete codeValue;
> > }
> > }
> >
> >
> > _______________________________________________
> > Qt-interest mailing list
> > Qt-interest at trolltech.com
> > http://lists.trolltech.com/mailman/listinfo/qt-interest
>
> _______________________________________________
> Qt-interest mailing list
> Qt-interest at trolltech.com
> http://lists.trolltech.com/mailman/listinfo/qt-interest
More information about the Qt-interest-old
mailing list