I have an issue that i just figured out what to do, so maybe you can help me.
I am working on a application that connects to a database, displays the values and allowes the user to update/insert values.
I have a QTabView and inside one of the tabs there are four QTableWidget's.
Inside this Tables is sometimes (depends on the value of the database) a QComboBox to select some predefined Values.
I catch the QComboBox::selectedIndexChanged(int) with a QSignalMapper and have a slot connected to the QSignalMapper to give some information what table it was and what setting was changed. From time to time i create the SettingsMapper new (and delete it before that) to reset the 'outdated' mapper-combobox connections.
So the problem is, that when i change the index inside a combobox, the slot gets called and i can debug into the moc_*.cpp where the switch of the signal/slot connections is, but after that i get the access violation on address 0xC0000005 inside the dlls.
Here the call stack:
QtCored4.dll!6721af70()
[Frames below may be incorrect and/or missing, no symbols loaded for QtCored4.dll]
QtCored4.dll!67219fe5()
QtCored4.dll!67218f14()
QtCored4.dll!67218e48()
QtCored4.dll!6721903d()
QtCored4.dll!6720f874()
QtCored4.dll!6702429b()
QtCored4.dll!670316f3()
QtGuid4.dll!655b93f1()
QtGuid4.dll!650f99d0()
user32.dll!7e41885a()
user32.dll!7e41882a()
user32.dll!7e42b326()
msctf.dll!7472467f()
user32.dll!7e43e1ad()
user32.dll!7e43e18a()
QtCored4.dll!67234b9c()
user32.dll!7e42b372()
user32.dll!7e418734()
user32.dll!7e418816()
user32.dll!7e4189cd()
user32.dll!7e418a10()
QtCored4.dll!672359b6()
ntdll.dll!7c90cfdc()
ntdll.dll!7c958e0d()
ntdll.dll!7c95932a()
ntdll.dll!7c90cfdc()
ntdll.dll!7c9594ca()
ntdll.dll!7c919ca7()
ntdll.dll!7c918f01()
ntdll.dll!7c91925d()
ntdll.dll!7c918f01()
ntdll.dll!7c9101bb()
ntdll.dll!7c9192ef()
ntdll.dll!7c918f01()
ntdll.dll!7c9101bb()
user32.dll!7e4277b0()
user32.dll!7e4277f7()
ntdll.dll!7c90da0c()
kernel32.dll!7c8024c7()
msctf.dll!74725951()
msctf.dll!74725956()
user32.dll!7e418a80()
user32.dll!7e418734()
user32.dll!7e418816()
ntdll.dll!7c96c6a7()
QtCored4.dll!6723c8f6()
datProgram.exe!__tmainCRTStartup() Line 578 + 0x35 bytes C
datProgram.exe.exe!WinMainCRTStartup() Line 403 C
kernel32.dll!7c817067()
`
What makes me curios is, that in another tab is one QTableWidget with the same methods as described above, but the problem does not occur there.
And when running in release version(Ctrl+F5) the problem also seems to be gone ... ò.Ó
Any advice?
From time to time i create the SettingsMapper
new (and delete it before that) to reset
the 'outdated' mapper-combobox connections.
Do you by any chance delete the signal mapper from a slot called by signal sent from that signal mapper? That's not allowed, can't delete the instance when you are currently in a method of that instance.
Solution is to use deleteLater() instead. That will cause the object to be deleted when control returns to event loop.
Related
I have two forms one is trainee_view.ui
and other is enter_new_trainee.ui
so for that i have trainee_view.cpp,trainee_view.h to see the list of Trainee in DB
and enter_new_trainee.cpp,enter_new_trainee.h to enter new trainee details
now in trainee_view.ui i have a push button "ADD Trainee"
so if i click this button it will go to "enter_new_trainee.ui"
void trainee_view::on_pushButton_2_clicked()
{
newtrainee=new enter_new_trainee(this);
newtrainee->setWindowFlags(Qt::Window);
newtrainee->show();
// connect(newtrainee, SIGNAL(destroyed()), this, SLOT(refresh_form()));
}
so by using connect() i am trying to refresh the trainee_view after entering the new trainee details. so how can i emmit the signal from
2nd form to 1st form such that i call refresh_form() method in 1st form .
I tried to use destroyed() signal on newtrainee but could not refresh my trainee_view form.
To be MOre simple . i just want to get an object is destroyed or not so if destroyed i can call refresh() method to load back the changes done on widget
for that i opted connect() method so how should i call that. becoz if i call
connect(newtrainee, SIGNAL(destroyed()), this, SLOT(refresh_form()));
there is no effect i.e nothing is loading into the view.
am newbie to qt so pls try to help me.
Thank YOu.
I'm not sure if I correctly understand your app, but I think you misunderstand the concept of Signals and Slots. Look here for some examples. In some simplification you can look at signal and slots this way: connect() command is a place which will not do anything - it just stay and keep listening for a signal. So you should place it in trainee_view.cpp. That's the first part and I see you did it correct, or almost correct. But you need also something that will send the signal, and this is exactly what emit() command do - it should be placed in enter_new_trainee.cpp just after description of generation new entry. For example, let assume user input new entry in LineEdit in UI:
[...]
QString newEntry = ui->LineEdit->text(); //Save entry to variable
emit(newEntry); //Emit it to signal slot
[...]
I want to do a Code Completer so i subclassed QCompleter:
http://hastebin.com/qeyumevisa.cpp
But, when I try to run this code, i get a runtime error:
And debug output shows:
ASSERT: "d->widget != 0" in file util\qcompleter.cpp, line 1446
Crash seems to come from the line 53:
QCompleter::complete(rect);
How i can fix this bug? Thanks
The assert is fired from QCompleter::complete(rect);
It means that QCompleter::widget() is zero. The private member d->widget is always initialized by zero. Its type is QPointer<QWidget>. The widget is set only by QCompleter::setWidget(QWidget *widget). According to the documentation QCompleter::setWidget(QWidget *widget):
Sets the widget for which completion are provided for to widget. This
function is automatically called when a QCompleter is set on a
QLineEdit using QLineEdit::setCompleter() or on a QComboBox using
QComboBox::setCompleter(). The widget needs to be set explicitly when
providing completions for custom widgets.
Thus, the widget must be set either by QCompleter::setWidget() or by QLineEdit::setCompleter(). If non of those options is used the function QCompleter::complete(rect) crashes if the completion mode is not QCompleter::InlineCompletion.
So, there are two possibilities for the crash:
d->widget is not initialized befor calling QCompleter::complete(rect);
since d->widget is a QPointer it can be automatically set to 0 when the referenced QWidget object is destroyed.
My application crashes, when I try to clear() all items from a QListWidget and at least one item is selected. Calling clearSelection() first causes the program to crash, too (at the clearSelection() call). Removing the items in a while loop, leads also to a crash. The error-message is
ASSERT: "!isEmpty()" in file /usr/include/qt4/QtCore/qlist.h, line 282.
Some example code:
void MainWindow::clearListWidget()
{
// ui->listWidget->clearSelection(); // --> causes crash
// ui->listWidget->clear(); // --> also causes crash
while(ui->listWidget->count()>0) // --> no crash calling count()
ui->listWidget->takeItem(0); // --> crash again
}
As mentioned, the application only crashes, if items are selected. If nothing is selected, then the methods above work as intended. I work with Qt 4.8.4 on Ubuntu.
I would be thankful for any suggestions, how I can solve the problem.
I have found a solution on my own. The problem was seemingly caused by accessing a selected item in a slot-method, that was connected to the signal itemSelectionChanged(). Here I accessed the text of the selected item via
string text = ui->listWidget->selectedItems().first()->text().toStdString();
Afterwards the crash appeared as described in my question by calling e.g. clear(). I guess the selection process is not finished, when itemSelectionChanged() is emitted and the QListWidget gets somehow confused, when the selected items are already accessed at this point of time. After replacing the signal by itemClicked(QListWidgetItem*), the application no longer crashed.
ui->listWidget->blockSignals(true);
ui->listWidget->clear();
ui->listWidget->blockSignals(false);
This worked in my case.
I need to block signals that I emit (indirectly) myself.
In C one could use g_signal_handlers_block_by_func() and the sister function unblock.
What can I use in C++ gtkmm?
I have a gtkmm dlna player, that emits the changed signal to a Gtk::HScale Widet each second, because it gets (from the outside) a signal that the song that just plays. And then I seek to the position that just where current, which set the song back a split second...
I would like to block my on changes from the seek, because I saw that a C program did that with g_signal_handlers_block_by_func.
since ptomato asked:
I never realized, that the connect method has a valuable return value:
so if you connect the signals like this:
mywidget_connection = mywidget.signal_value_changed().connect(sigc::mem_fun(*this, &MyClass::on_value_changed ));
In my situation I have 2 ways to change the value:
1.) someone pulls a slider: should update the value and seek
2.) the timer comes along and tells the new position: should update the value but not seek.
then you can block/unblock like this:
mywidget_connection.block();
mywidget.set_value(new_value);
mywidget_connection.unblock();
and this does not emit the changed signal.
I am writing a console application that allows you to use ECMAScript to move the mouse about, and define hot keys etc. The mouse stuff works, and now I am trying to add in the ability to define hot keys that when pressed will call a QtScript handler function.
The problem is, when I try to use QxtGlobalShortcut to create the hot key, I get a SIGSEGV and everything crashes.
Here is the code:
int Keyboard::hot_key(QString key) {
QxtGlobalShortcut shortcut;
shortcut.setShortcut(QKeySequence(key));
shortcut.setEnabled(true);
connect(&shortcut, SIGNAL(activated()), this, SLOT(hot_key_pressed()));
return 0;
}
This line QxtGlobalShortcut shortcut;, if I gut the entire function except for that line, it still throws a seg fault.
And the debugger says:
1 ZNK17QxtGlobalShortcut8shortcutEv C:\Qxt\lib\QxtGui.dll 0 0x6f6f14a6
2 ZN17QxtGlobalShortcutC1EP7QObject C:\Qxt\lib\QxtGui.dll 0 0x6f6f14f7
3 Keyboard::hot_key keyboard.cpp 16 0x403c0c
4 Keyboard::qt_metacall moc_keyboard.cpp 74 0x404740
5 QMetaObject::metacall qmetaobject.cpp 237 0x8f5ff8
Considering how not so easy, in my opinion, Windows hotkeys are, I'd really like to use Qxt, but so far I am just hitting a wall. If anyone could point me in the right direction, or even recommend some other library that might be able to help me, or a tutorial on hotkeys that would be awesome.
Thanks in advance!
Your shortcut object is constructed on the stack. It will get deleted as soon you leave that function, so your code is bound to fail even if it did not die in that function.
You should be creating that object with:
QxtGlobalShortcut *shortcut = new QxtGlobalShortcut;
If you care about not leaking that, store that pointer as a member of your class and delete it in it's destructor.
As for the crash, that could happen if you are using a version of Qxt older than 6.0 and haven't initialized a QxtApplication yet.