Editing items in custom QTableWidget
-
Hi everybody! I have some problems and can't solve them. I have custom table and custom delegate. By default item starts editing when user press button on keyboard. First, I need to change this so that the cell goes into edit mode when I click on the hex characters (0-9, A-F). After that, I need to write two hexadecimal characters, at most. After item filling, automatically close editing mode and go to next item. Below is the code for the keyPressEvent function and all the code for my delegate.
void MemoryTable::keyPressEvent(QKeyEvent *event) { if(!editingMode) return; else { if((event->key() >= Qt::Key_0 && event->key() <= Qt::Key_9) || (event->key() >= Qt::Key_A && event->key() <= Qt::Key_F)){ QTableWidgetItem *item = currentItem(); if(item) openPersistentEditor(item); } else if(event->key() == Qt::Key_Left){ moveToPreviousCell(); } else if(event->key() == Qt::Key_Right){ moveToNextCell(); } else QTableWidget::keyPressEvent(event); } }
Custom delegate:
#include "mydelegate.h" #include <QDebug> void MyDelegate::CommitAndCloseEditorNonConst() { QLineEdit* editor = qobject_cast<QLineEdit*>(sender()); emit CommitAndCloseEditor(); } QWidget *MyDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const { (void)option; (void)index; QLineEdit *editor = new QLineEdit(parent); connect(editor, &QLineEdit::editingFinished, this, &MyDelegate::CommitAndCloseEditor); return editor; } void MyDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const { QLineEdit *lineEdit = static_cast<QLineEdit*>(editor); lineEdit->setInputMask("HH"); lineEdit->setText(index.data().toString().toUpper()); } void MyDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const { QLineEdit *lineEdit = static_cast<QLineEdit*>(editor); model->setData(index, lineEdit->text(), Qt::EditRole); } void MyDelegate::CommitAndCloseEditor() { QLineEdit* editor = qobject_cast<QLineEdit*>(sender()); emit commitData(editor); emit closeEditor(editor); }
Thank you in advance for your help.
-
Hi and welcome to devnet,
You should change your view's editTrigger to adapt it to your needs.
As for your editor, you can set an input mask to limit what can be written in it.
-
In your MemoryTable constructor. As for the value, doesn't SelectedClicked do what you want ?
-
@SGaist No, I need realize start edit item when user press buttons 0-9 or a-f or A-F. And after user input 2 hexadecimal characters, program should finish edit item and go to next item. It's not my whim, that's how the task was set :)
-
In that case, it seems that you need to disable the edit triggers completely and then indeed manage that with keyPressEvent. You then need to set the the original key in the editor you just opened.
You need then to implement a custom QLineEdit to trigger the editor closing when the second value is entered in it using for example textEdited.
-
-
@JonB I'm just not quite sure at what point I would need to close the editor itself. In keyPressEvent I put the cell in edit mode, and then the work goes to the user delegate. But then I can't see where exactly I need to close the editor.
-
@Vladosik02
Like you said: "automatically close it after writing 2 characters". You're using key press events, somehow you know when the user has typed the second character, that is when to (validate input and) close the editor and move to next cell. -
@JonB I have a custom delegate, I specified its code above. In setEditorData I have an input mask. By default, the editor can be closed by pressing Enter, Escape, or Tab/Shift+Tab buttons. If I understand correctly, when calling openPersistentEditor the work goes to MyDelegate. That's why I don't quite understand where it would be appropriate to call closePersistentEditor.
Speaking of which, maybe you know if I click on a symbol and open the editor via editItem, how do I immediately put that symbol inside the cell? Because it appears that the editor opens when I click on a symbol, but there is just selected text and I have to click on the symbol again to enter it.
-
@Vladosik02 said in Editing items in custom QTableWidget:
That's why I don't quite understand where it would be appropriate to call closePersistentEditor.
When the user presses the second key or fills the second input or whatever it is you want to terminate editing. (I think the input mask only controls what you can enter, I don't think it will treat typing the two characters as terminating editing.)
One way suggested by @Sgaist was:
You need then to implement a custom QLineEdit to trigger the editor closing when the second value is entered in it using for example textEdited.
Did you look at that?
-
@JonB said in Editing items in custom QTableWidget:
Did you look at that?
Yes, I saw this. I'll try. By the way, after I open the editor, supposedly the keyPressEvent in the table no longer tracks button presses until the edit is completed
-
@Vladosik02
Yes, follow his link to void QLineEdit::textEdited(const QString &text). It would be nice if you then emitted eitherreturnPressed
oreditingFinished
signal on detecting 2 characters/keys. I think that would might exit the editor without needing toclosePersistentEditor()
as it would do it for you. However I see docs say these are not emitted if content fails either input mask or validator. I don't know if that means you have to do your own checking of these before emitting those signals. Having said that, since the only acceptable input is 2 hexadecimal digits it's not too hard to do your own check without having to deal with the result of input mask/validator.Yes I imagine that while the editor is open all key presses go only to it, not to the table.
-