PDA

View Full Version : Trying to show a QDialog



jimbo
16th September 2017, 12:57
Hello,

Trying to show a QDialog, but I am getting the errors shown.
What am I doing wrong?

Regards


Header
#ifndef QG_DIVIDEOPTIONS_H
#define QG_DIVIDEOPTIONS_H

#include <QDialog>

namespace Ui {
class qg_divideoptions;
}

class qg_divideoptions : public QDialog
{
Q_OBJECT

public:
explicit qg_divideoptions(QWidget *parent = 0);
~qg_divideoptions;

private:
Ui::qg_divideoptions *ui;

};
#endif // QG_DIVIDEOPTIONS_H
qg_divideoptions.cpp
#include <QtGui>
#include "qg_divideoptions.h"

qg_divideoptions::qg_divideoptions(QWidget *parent) : //*** qg_divideoptions does not name a type
QDialog(parent),
ui(new Ui::qg_divideoptions)
{
ui->setupUi(this);
}
Calling function header
public:
QDialog* mydialog;
Calling function
#include "qg_divideoptions.h"
#include <QDialog>

void myfunc::mouseReleaseEvent(QMouseEvent* e) {
if (e->button() == Qt::LeftButton) {
qg_divideoptions mydialog = new qg_pdivideoptions(); //*** qg_divideoptions was not declared in this scope
mydialog->show(); //*** mydialog was not declared in this scope
}
}

d_stranz
16th September 2017, 16:47
I can't see any syntactic problems with this code that could cause this problem. The only thing I can think of is you have two files called "qg_divideoptions.h", one of which is empty or does not contain the definition of your class, and that is the one being #include-ed by mistake. Or, because lowercase "q" and "g" look so similar, you might have a "q" where a "g" should be (or vice-versa) and you don't see it because you have to look very closely at the text to tell the two apart. "qq", "qg", "gq", and "gg" all look pretty much the same if you aren't looking carefully. I would choose a different name to make maintenance and debugging easier.

In your mouseReleaseEvent, you have a memory leak. Each time this event executes, you are creating new copy of the dialog and assigning it to a local variable in the function. Once the function exits, you have a dangling pointer that isn't accessible for you to delete the dialog instance later.

Better is to create the dialog on the stack and execute it as a modal dialog:



void myfunc::mouseReleaseEvent(QMouseEvent* e) {
if (e->button() == Qt::LeftButton) {
qg_divideoptions mydialog( this );
if ( QDialog::Accepted == mydialog.exec() )
// do something with the result
}
}

Of course, if I were a user of your software and this *^%&@ dialog kept popping up every time I clicked the mouse button by accident I'd probably become an ex-user pretty quickly. Maybe something more user-friendly, like a context menu that let me choose to show the dialog would be nicer.

jimbo
17th September 2017, 10:44
Hello d_stranz,

Thanks for your reply.


"qq", "qg", "gq", and "gg" all look pretty much the sameYes I know, its somebody elses program, I'm stuck with it.


*^%&@ dialog kept popping up every timeThere are checks in place, as to when its allowed to pop up.

The two files bit, turns out it was a suspect HDD data lead, was editing the wrong file.

Your point is noted about show() and exec().

I will know in about 7 hours, doing a rebuild.

Regards

jimbo
19th September 2017, 13:53
Hello.

Back on this now.
I did a fresh build and got the following errors.
Help Please!

Regards


#ifndef QG_DIVIDEOPTIONS_H
#define QG_DIVIDEOPTIONS_H

#include <QDialog>
//#include <ui_qg_divideoptions.h>

namespace Ui {
class qg_divideoptions;
}

class qg_divideoptions : public QDialog
{
Q_OBJECT

public:
explicit qg_divideoptions(QWidget *parent = 0);
~qg_divideoptions();

private:
Ui::qg_divideoptions *ui;

signals:

private slots:
};
#endif // QG_DIVIDEOPTIONS_H
#include <QtGui>
#include <QDialog>

#include "qg_divideoptions.h" //this is qg_divideoptions.cpp:29
#include <ui_qg_divideoptions.h>

qg_divideoptions::qg_divideoptions(QWidget *parent) :
QDialog(parent),
ui(new Ui::qg_divideoptions) // invalid use of incomplete type 'class Ui::qg_divideoptions'
// In file included from ...\qg_divideoptions.cpp:29:
// forward declaration of 'class Ui::qg_divideoptions'
{
ui->setupUi( this ); // invalid use of incomplete type 'class Ui::qg_divideoptions'
// In file included from ...\qg_divideoptions.cpp:29:
// forward declaration of 'class Ui::qg_divideoptions'
}

qg_divideoptions::~qg_divideoptions()
{
//saveSettings();
qDebug() << "end";
}

d_stranz
19th September 2017, 17:49
It indicates that the "qg_divideoptions.ui" file (or the ui_qg_divideoptions.h" file generated from it by the resource compiler) is wrong.

I think you need to spend some time cleaning up your project and file environment and making sure that the duplicate copies of things you seem to have laying around are gone and that your project and the include paths points to the right files in the right locations.

Your use of "#include <ui_qg_divideoptions.h>" instead of "#include "ui_qg_divideoptions.h"" is a red flag. When you use "<>" instead of quotes, it is telling the compiler not to look in the current directory for a file, but to look somewhere else along the list of include paths. That tells me the compiler is probably using the wrong file.

jimbo
29th September 2017, 13:20
Hello,

Thanks for your help.
My main problem was a dying mother board (fixed now) and
the rest of the problem is my ignorance.
I created a new source directory and compiled from there.

I've still got problems, that I don't understand.

Regards

Call
qg_divideoptions mydialog( 0 );// this );
//using 'this' :-
//error: no matching function for call to
//'qg_divideoptions::qg_divideoptions(RS_ActionModif yCut*)'
//'RS_ActionModifyCut' is the function the above call is in.

if ( QDialog::Accepted == mydialog.exec() )
{
// do something with the result
qDebug() << "accepted";
}
else
{
qDebug() << "rejected";
}
Header

#ifndef QG_DIVIDEOPTIONS_H
#define QG_DIVIDEOPTIONS_H

#include <QtGui>
#include <QDialog>


namespace Ui {
class qg_divideoptions; //forward declaration of 'class Ui::qg_divideoptions'
}

class qg_divideoptions : public QDialog
{
Q_OBJECT

public:
qg_divideoptions(QWidget *parent = 0);
~qg_divideoptions();

private:
Ui::qg_divideoptions *ui;

signals:

private slots:

}

#endif // QG_DIVIDEOPTIONS_H


qg_divideoptions.cpp

#include <QtGui>

#include <QDialog>
#include <QWidget>

#include "qg_divideoptions.h"
#include <QDebug>


qg_divideoptions::qg_divideoptions(QWidget *parent) :
QDialog(parent),
ui(new Ui::qg_divideoptions) //error: invalid use of incomplete type 'class Ui::qg_divideoptions'
{
ui->setupUi(this); //error: invalid use of incomplete type 'class Ui::qg_divideoptions'
}

qg_divideoptions::~qg_divideoptions()
{
qDebug() << "deleted";
}
qg_divideoptions.ui

<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>divodeoptions</class>
<widget class="QDialog" name="divodeoptions">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>400</width>
<height>300</height>
</rect>
</property>
<property name="windowTitle">
<string>Divide Options</string>
</property>
</widget>
<resources/>
<connections/>
</ui>

d_stranz
29th September 2017, 21:26
ui(new Ui::qg_divideoptions) //error: invalid use of incomplete type 'class Ui::qg_divideoptions'

ui->setupUi(this); //error: invalid use of incomplete type 'class Ui::qg_divideoptions'


You haven't #include'd the ui_...h file for your ui class. You forward-declared it in the header file, but never included the file that contains the implementation.

I have no idea what is causing the first error. You haven't included the full source code for the function, so there is no information about the context in which you are trying to create your dialog.

jimbo
30th September 2017, 15:19
Hello,

Again thanks for your help.

Windows 10 - 32bit

I'm building from within Qt Creator.

About:-
Qt Creator 4.4.0
Based on Qt 5.9.1 (MSVC 2015, 32 bit)

gcc version 5.3.0 (i686-posix-dwarf-rev0, Built by MinGW-W64 project)

Still getting the same errors,


#include <QtGui>

#include <QDialog>
#include <QWidget>

#include "qg_divideoptions.h"
#include "ui_qg_divideoptions.h" //*** added
#include <QDebug>

qg_divideoptions::qg_divideoptions(QWidget *parent) :
QDialog(parent),
ui(new Ui::qg_divideoptions)
{
ui->setupUi(this);
}

qg_divideoptions::~qg_divideoptions()
{
qDebug() << "deleted";
}
rs_actionmodifycut.h

private:
QDialog *mydialog;
rs_actionmodifycut.cpp

#include "rs_actionmodifycut.h"

#include <QAction>
#include <QMouseEvent>
#include "rs_dialogfactory.h"
#include "rs_graphicview.h"
#include "rs_modification.h"
#include "rs_debug.h"

//*** ***
#include <QDialog>
#include <QDebug>
#include "qg_divideoptions.h"
//*** ***

RS_ActionModifyCut::RS_ActionModifyCut(RS_EntityCo ntainer& container,
RS_GraphicView& graphicView)
:RS_ActionInterface("Cut Entity",
container, graphicView)
,cutEntity(nullptr)
,cutCoord(new RS_Vector{})
{
actionType=RS2::ActionModifyCut;
}

void RS_ActionModifyCut::mouseReleaseEvent(QMouseEvent* e) {
if (e->button()==Qt::LeftButton) {
switch (getStatus()) {
case ChooseCutEntity:
cutEntity = catchEntity(e);
if (cutEntity==nullptr) {
RS_DIALOGFACTORY->commandMessage(tr("No Entity found."));
} else if(cutEntity->trimmable()){
cutEntity->setHighlighted(true);
graphicView->drawEntity(cutEntity);
setStatus(SetCutCoord);

//*** ***
qg_divideoptions mydialog( 0 );// this );

if ( QDialog::Accepted == mydialog.exec() )
{
// do something with the result
qDebug() << "accepted";
}
else
{
qDebug() << "rejected";
}
//*** ***

}else
RS_DIALOGFACTORY->commandMessage(
tr("Entity must be a line, arc, circle, ellipse or interpolation spline."));
break;

case SetCutCoord:
*cutCoord = snapPoint(e);
if (cutEntity==nullptr) {
RS_DIALOGFACTORY->commandMessage(tr("No Entity found."));
} else if (!cutCoord->valid) {
RS_DIALOGFACTORY->commandMessage(tr("Cutting point is invalid."));
} else if (!cutEntity->isPointOnEntity(*cutCoord)) {
RS_DIALOGFACTORY->commandMessage(
tr("Cutting point is not on entity."));
} else {
trigger();
deleteSnapper();
}

qDebug() << "released";
break;

default:
break;
}
} else if (e->button()==Qt::RightButton) {
if (cutEntity) {
cutEntity->setHighlighted(false);
graphicView->drawEntity(cutEntity);
}
init(getStatus()-1);
}
}

//Rest of the functions
...
...

d_stranz
30th September 2017, 17:05
rs_actionmodifycut.h

I should be paid as much as my dentist - I am spending almost as much time pulling teeth here. What Qt class is "RS_ActionModifyCut" ultimately derived from?

Look, it is basic C++: any QWidget-based class takes an optional pointer to its parent QWidget as an argument to its constructor. This includes QDialog and classes derived from QDialog. If you try to pass in a pointer to a class that is not derived from QWidget, then you will get a compile-time error. Passing "0" always works, because a zero can be cast to a pointer of any type. Passing "this" will work only if the class that "this" is an instance of is derived ultimately from QWidget.