PDA

View Full Version : Multiple Classes setText Update



Msnforum
27th January 2009, 23:00
I have two classes: class A and B. class A inherits QWidget and class B inherits class A.

When a button is clicked, it connects to a slot in class A that creates an object of class B.
After the http request is done in class B, it executes a function from the base class that changes the text of the button.

Everything runs except the button doesn't update at all. qDebug shows the label as the new text but on GUI, it is still displaying the old text. I tried update() and repaint() but none works.


class A : public QWidget
{
Q_OBJECT
public:
A();
void clickPressed();
private slots:
void changeButtonText();
private:
QPushButton *button;
};

A::A()
{
button = new QPushButton(tr("Hello"));
connect(button,SIGNAL(clicked()),this,SLOT(clickPr essed()));
}

void A::changeButtonText()
{
button->setText(tr("again"));
}

void A::clickPressed()
{
B *objectB = new B;
}


class B : public A
{
Q_OBJECT
public:
B();
private slots:
void requestDone();
private:
QHttp *http;
};

B::B()
{
http = new QHttp(this);
....
connect(http,SIGNAL(done(bool)),this,SLOT(requestD one(bool)));
}

B::requestDone(bool error)
{
...
changeButtonText();
}

I wrote the above as an example to my problem.

wysota
28th January 2009, 02:00
Could you prepare something we could compile and run? The above code doesn't say much - it seems valid but it could be that the problem is elsewhere, for example you might be blocking the event loop somewhere with a while() (or similar) loop. You could try adding QApplication::processEvents() after you change the text and see if it helps. If it does then you are indeed blocking the loop, if not - add a qDebug() statement to see if the slot is executed at all.

Msnforum
28th January 2009, 07:05
Ok, here goes. This is the simplified version which represents the problem.

main.cpp

#include <QApplication>
#include "a.h"

int main(int argc, char *argv[]){

QApplication app(argc, argv);

A a;
a.show();

return app.exec();
}

a.h

#ifndef A_H
#define A_H

#include <QWidget>
#include <QPushButton>
#include <QVBoxLayout>
#include <QApplication>
#include <qDebug>

class A : public QWidget
{
Q_OBJECT
public:
A();
void changeButtonText();

public slots:
void buttonPressed();
private:
QPushButton *button;
QVBoxLayout *layout;
};

#endif

a.cpp

#include "a.h"
#include "b.h"

A::A()
{
layout = new QVBoxLayout();
setLayout(layout);
button = new QPushButton(tr("try"));
connect(button,SIGNAL(clicked()),this,SLOT(buttonP ressed()));

layout->addWidget(button);
}

void A::buttonPressed()
{
B *ObjectB;
ObjectB = new B;
}

void A::changeButtonText()
{
button->setText(tr("here"));
QApplication::processEvents();
qDebug(button->text().toLocal8Bit());
}

b.h

#ifndef B_H
#define B_H

#include "a.h"

class B : public A
{
Q_OBJECT
public:
B();
};

#endif

b.cpp

#include "b.h"

B::B()
{
changeButtonText();
}

Test.pro

TEMPLATE = app
CONFIG += qt warn_on embed_manifest_exe console
QT += network
TARGET = Test
SOURCES = main.cpp a.cpp b.cpp
HEADERS = a.h b.h
LIBS +=


# Treat warnings as errors
win32:QMAKE_CXXFLAGS += /WX

CONFIG(debug, debug|release){
# Debug build options
# Enable a read-only console window (i.e. for printf etc.)
# CONFIG += console
}
else{
# Release build options
# Enable a read-only console window (i.e. for printf etc.)
# CONFIG += console
}

Msnforum
28th January 2009, 19:55
Instead of putting everything in codes, I've decided to put it as attachments. Sorry for double posting though. The .pro file is on previous post.

Msnforum
30th January 2009, 11:38
cough... I really need guidance on this.

Lykurg
30th January 2009, 16:40
Well the displayed text couldn't be changed! Why, B creates a new instance of A where the Text is changed. The B::A has nothing to do with your class A created in main().

If you want to interact between A and B use a proper signal and slot mechanism. (EDIT: Or give the constructor of B a pointer to A)


Lykurg