QSpinbox editingFInished signal on up/down arrow press - qt

I went through a lot of posts regarding QSpinBox signals editingFinished and valueChanged, but not able solve my problem, ie,
I want editingFinished signal to be emitted, when user enters any value and presses "Enter".[DONE]
The user can change value with the up/down arrows either by keyPress or mousePress. This can be done by valueChange signal, but not editingFinished
So to achieve both, I'm facing problem, Suppose I want to enter 10000, so valueChanged is emitted with 1, 10, 100, 1000, 10000
Which I don't want, rather it should emit when user pressed enter after entering 10000.
So this is done by avoiding valueChanged and connecting to &QAbstractSpinbox::editingFinished.
connect(ui->spinBox, &QSpinBox::editingFinished,
this, [&]()
{
ui->label->setText(QString::number(ui->spinBox->value()));
});
But I want the up/down arrows to work also. so for this again valueChanged is required.
Is there any means to achieve it directly, rather than adding my own spinbox class and overriding the events for up/down arrow click/press.
Any suggestion is appreciated.

I think what you're looking for is to ensure that the keyboardTracking property is disabled (set to false). The property is true by default in most cases.
As the Qt docs state, with keyboardTracking on false you'll only get valueChanged() (and textChanged() in Qt 5.14+) signals once Enter is pressed in the spin box (or if user tabs away or the field otherwise looses focus), not while text is being edited.

Not clear why, but this does what you need:
set the keyboardTracking property of the spinbox to false, then do the following:
void MainWindow::on_mySpinBox_valueChanged(int arg1)
{
on_mySpinBox_editingFinished();
}
void MainWindow::on_mySpinBox_editingFinished()
{
// what you need to be done, on spinbox loosing focus or arrows adjusting (and not while editing)
}

Related

Letting another widget handle your events in Qt

I have a QSpinBox in a QMainWindow holding a value. Natively the spinbox, well ... spins on QWheelEvent if focused. I would like to expand the scrolling of the value in the spinbox to be applied invariantly of focus within the window.
The spinbox manages a value that dictates behavior to the whole context of the window live.
I am trying to divert the scroll event to the spinbox to be handled by the latter to implement this instead of handling a custom value somewhere and to synchronize it with the spinbox manually.
But I am failing. I have an EventFilter in the window that can intercept the event in the window invariantly of focus, but the wheelEvent method in the spinbox is protected so I cannot call it from there.
I do not want to just make a custom spinbox for this if I can help it.
Any ideas?
In the event filter, do not call the protected spinBox->wheelEvent(wheelEvent). You can instead pass the event to the spin box using static function QCoreApplication::sendEvent(spinBox, wheelEvent).
Of course, seeing your code would help to show more concrete solution. Especially you should make sure that your event filter does not intercept this re-sent event again, creating an infinite loop...

QAction Qt::Key_Return shortcut is triggered by user entering values in GUI

I have an issue with associating a keypress to a QAction. I'm mapping Enter to an action like this:
myAction->setShortcut(Qt::Key_Return);
The problem is that the QAction is also triggered when I type a value in a QSpinBox and then press Enter. I was expecting the spinbox to consume the event (so it's not caught by the mainwindow) but it's not working like that.
I've seen that I can add a context to my shortcut, I tried all values but this does not solve my issue.
#Matthew It is indeed rejecting the event:
case Qt::Key_Enter:
case Qt::Key_Return:
d->edit->d_func()->control->clearUndo();
d->interpret(d->keyboardTracking ? AlwaysEmit : EmitIfChanged);
selectAll();
event->ignore();
emit editingFinished();
return;
I find this behavior quite strange.
From my knowledge the QSpinBox default behavior does wait until you press return to accept the value. Technically the value is set/accepted as soon as you change it.
If you're looking to change that behaviour, i.e. when you hit return on your QSpinBox you the value is actually set/accepted, then you will most likely have to handle the associated key press event yourself on the QSpinBox and mark it as accepted (i.e. event->accepted() ).
Otherwise, this sounds like it is working as originally designed although not as you want.
I have exactly the same problem, only in PyQt and with QLineEdit
It may be that QActions are always considered menu actions, or global, and have a higher priority than Widget Default keys.
My "solution" was to create a global list of my actions with important keys (Return, Tab, Backspace etc.) as shortcuts.
Then I hook into QLineEdit focusInEvent and focusOutEvent. Each time the event happens I loop over the actions-list and deactivate them all on focusIn and activate them again on focusOut. Then I give the event to the original focus event handlers.
I really hope there is a better solution.

qt/pyqt how to make spinbox-signal only for user action/event?

I need to react(make event) only to user action, but program has to be able to change value too, but without event.
If I use comboBox is there signal activated(int) for this reason. How can I do it for spin-box?
There isn't an activated for the spinbox because the only activation is to click on the button - which sends a change signal
You can always set the value of the spinbox with spinBox->setValue(value);
edit: you want to set a spinbox without having it emit a signal ?
Best way is for the setter to temporarily disable signals from the control with QObject::blockSignals()

QTableView: Best way to change activation-trigger to double-click

In my application, I have one tableview of items, and a side-panel "preview":ing the latest selected item.
I want clicking on an item to change the selection, and double-clicking to cause a "run"-action to be performed. More specifically, I want the "run"-action (including key-navigation and pressing enter) to be bound to the "activation" of the item in the table-row.
My problem is; single-clicks does not only change the selection, but fires the "activated" signal on the item. I would like to tweak it such that:
Navigation Keys, Single Mouse Click: Selection-change, update preview-panel
Enter Key, Double Mouse Click: Activate/run/open action triggered.
Is there a nice clean way to do it, or are overriding the onclick/doubleclick events my best option? Or is there some other tabular list-widget better suiting my needs?
I would connect the slot for the preview action to the currentChanged() signal of the table view's selectionModel(). This covers single clicks and key navigation.
Then there's two options for the double clicks and Enter key presses:
Subclass your tableview, override doubleClickEvent() and keyPressEvent() and fire your custom signal in there, with maybe the model index or something else as an argument. Then just connect your run method to your own signal as you have full control over when it is fired.
If you don't want to subclass, you can use the installEventFilter() mechanism.
Either I'm getting your approach wrong or I'm too tired, but if you want to trigger a run event you should avoid the activated signal completely. Set the signal slot mechanism so that your double click and Enter key press event trigger your run() function, and then the single click/nav buttons should trigger the 'activated' slot which will return your index in the tableview.
I'm pretty certain Qt wants you to be explicit about which signal points to which slot or it'll ignore it or point to a default.

Qt - Radiobutton in diff dialog(window) -> taking result to the mainwindow into lineedit

my problem looks like that. I got dialog window and i know how to get result from checked radiobutton but only in this window. How to take result into different window(mainwindow).
button(Pobierz) is on mainwindow and close to this button is lineedit2 where i would like to take result from checked radiobutton, but dont know how. I make lineedit in this new Dialog window and its taking result, but i dont know how to take this result into mainwindow. Hope I explain good enough. Thanks for any help.
void Pobierz::on_pushButton_clicked()
{
if(ui->radioButton1->isChecked())
{
ui->lineEdit->setText("K");
}
if(ui->radioButton2->isChecked())
{
ui->lineEdit->setText("S");
}
if(ui->radioButton3->isChecked())
{
ui->lineEdit->setText("I");
}
}
Greetings,Tom.
up1
i tried couple ways but still cant solve this..
In your class for the dialog, declare a signal that passes a QString. Also override the accept function (if you don't already). In the accept function, emit the signal with the appropriate string according to the radio buttons. (Don't forget to call the parent accept function in your own).
In your class for the main window, when you create the dialog, connect the signal from the dialog to a slot that sets the text in the line edit in the main window. When the dialog is accepted, the signal should fire, running the slot in the main dialog, adding the appropriate text to the line edit.
Create a slot in the main window which would get the radio button status from the dialog window. In this slot set your main window's lineedit based on the result from the dialog window radio button checked status.
While creating the radio button on the dialog window, connect the radio button's clicked signal with the main window's slot defined earlier.

Resources