Delegates and relational table views



  • Hi :)

    I am using QSqlRelationalDelegate into a QSqlRelationalTableView, which works fine.

    However I'd like the combo box to be able to filter as I type, because it holds several thousands of items. I'd like to know if this can be implemented with this kind of delegate or if I should be looking at QStyledDelegate or something else instead.

    Having filter capabilities in the delegate would also be nice, though I think I can solve that in some other way.

    I have read the documentation, but the QSqlRelationalDelegate page is so so simple that I am really wondering if that's really all that there's to it. Still learning as I go :)

    Thanks everyone.


  • Moderators

    so you have an editable comobox as an editor?
    If so you can use QComboBox::setCompleter() on the editor widget (combobox)



  • [quote author="raven-worx" date="1376469355"]so you have an editable comobox as an editor?
    If so you can use QComboBox::setCompleter() on the editor widget (combobox)[/quote]

    I don't really know. It's a combo box, but I have no idea how qt handles this internally. I am using QSqlRelationalDelegate, this way:

    [code]
    ui->tableView_cascosYAccesorios->setItemDelegate(new QSqlRelationalDelegate(ui->tableView_cascosYAccesorios));
    [/code]

    With whatever "editor" it uses by default. I have also tried to declare the delegate separately, but I have no idea how to access its editor, if that's even possible.

    That's why I am wondering if I should use another kind of delegate which is more flexible...

    Thanks for your help :)



  • Right now, I have this:

    [code]
    class MySqlDelegate : public QSqlRelationalDelegate
    {
    Q_OBJECT
    public:
    explicit MySqlDelegate(QObject *parent = 0);

    signals:

    public slots:
    void setEditorData ( QWidget * editor, const QModelIndex & index ) const
    {
    QSqlRelationalDelegate::setEditorData(editor, index);

        QComboBox* comboBox = qobject_cast<QComboBox*>(editor);
        comboBox->setEditable(true);
        if( comboBox )
        {
            QCompleter* completer = new QCompleter(comboBox);
            completer->setCompletionColumn(index.column());
            completer->setCompletionMode(QCompleter::PopupCompletion);
            completer->setWrapAround(true);
            completer->setMaxVisibleItems(10);
            completer->setCaseSensitivity(Qt::CaseInsensitive);
            comboBox->setCompleter(completer);
            connect(comboBox, SIGNAL(editTextChanged(QString)),
                    completer, SLOT(setCompletionPrefix(QString)));
        }
    }
    

    };
    [/code]

    It seems the setEditable(true) bit got me as far as to being able to actually edit the combobox, however the filtering doesn't seem to work and I get no popup.

    The popup works ok and shows all the elements if I click the down arrow icon, of course. Which is why I know that the combobox has been populated as it should.

    I also tried connecting the things in some manner, but it didn't make a difference. Please, don't lauch at me :)

    It's my first time with delegates, so, you know... :P

    Thank you everyone.


  • Moderators

    so did it solve your problem or do you still have an issue?



  • Nope, sorry for not being so clear.

    It doesn't seem to actually filter anything, and the popup doesn't appear as I write.

    I'd also like the QComboBox field empty on the first keypress, but that's the not my bigest problem right now, and I should be able to figure that out eventually (or so I hope).

    I am having some trouble to find QCompleter/QComboBox examples in the net, plus I don't really know what QSqlRelationalDelegate does under the hood.

    I think I need some coffee, then I'll get back to this ;)


  • Moderators

    just some additions to your code:
    put the "comboBox->setEditable(true)" inside the if statement to avoid possible crashes.

    I don't think that you need to connect the completer explicitly. It should be enough to just set it on the combobox.



  • [quote author="raven-worx" date="1376490168"]just some additions to your code:
    put the "comboBox->setEditable(true)" inside the if statement to avoid possible crashes.[/quote]

    Thanks, that makes sense.

    [quote]
    I don't think that you need to connect the completer explicitly. It should be enough to just set it on the combobox.[/quote]

    That's what I thought. After all, I am subclassing a completelly functional critter, but it doesn't seem to do a thing (it doesn't do a thing after the explicit connection either, so...).

    The items are there, in the popup and I can select them with the mouse. But they are not affected by any kind of filtering, it doesn't matter what I write in the box.


  • Moderators

    ok i think the QCompleter is missing it's values ;)

    Try this:
    @
    class MySqlDelegate : public QSqlRelationalDelegate
    {
    Q_OBJECT

    public:
        explicit MySqlDelegate(QObject *parent = 0);
      
        void setEditorData ( QWidget * editor, const QModelIndex & index ) const
        {
            QSqlRelationalDelegate::setEditorData(editor, index);
     
            QComboBox* comboBox = qobject_cast<QComboBox*>(editor);
            if( comboBox )
            {
                comboBox->setEditable(true);
    
                QCompleter* completer = new QCompleter(index.model(), comboBox);
                completer->setCompletionColumn(index.column());
                 completer->setCompletionMode(QCompleter::PopupCompletion);
                completer->setWrapAround(true);
                completer->setMaxVisibleItems(10);
                completer->setCaseSensitivity(Qt::CaseInsensitive);
                comboBox->setCompleter(completer);
            }
        }
    };
    

    @



  • I can't seem to be able to do that. I can't use setModel() either, not on a const QModelIndex& argument... I'll continue trying things, but I'd really appreciate a good book on models, indexes, records, and that stuff. Right now it's all a wonderful spaghetti to me :P

    Your help is much appreciated. Thanks again.



  • It seems that we also need to reimplement the method for the model. I ended up using this:

    http://qt-project.org/wiki/QSqlRelationalDelegate-subclass-for-QSqlRelationalTableModel

    Which "just works" after setting the edit capabilities to true, just as before. I promise to get back to this some day, but I've lost a whole day in this and I am in a bit of a hurry now.

    Thank you a ton, this has been quite illustrative, but for now it's a bit over my head. :(


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.