Results 1 to 4 of 4

Thread: slot control of new function

  1. #1
    Join Date
    Nov 2007
    Posts
    103
    Thanks
    71
    Thanked 2 Times in 2 Posts
    Qt products
    Qt4
    Platforms
    Windows

    Default slot control of new function

    Hi guys,

    I learned from danbetz to create new functions and started experimenting with how to turn on the new function using signals/slots. I wrote a code (see below) that displays a button and when the button is clicked something should be drawn above the button. The code compiles fine but no drawing appears when I click the button. Does anyone know why? I'm hugely thankful, as always.
    I suspect that the setPixmap(pm) part is the problem, or the picture is not refreshed for some reason, or maybe the slot is declared incorrectly.

    ////////////////////////////The *.h file//////////////////////////////////////
    #ifndef TOM_H
    #define TOM_H

    #include <QObject>
    #include <QPixmap>

    class QObject;
    class QPixmap;

    class MySlot : public QObject
    {
    Q_OBJECT

    public:
    MySlot (QObject *parent = 0);

    public slots:
    QPixmap testDraw();
    };
    #endif

    ///////////////////The main file///////////////////////////////////
    #include <QtGui>
    #include "tom.h"

    MySlot::MySlot(QObject *parent):QObject(parent)
    {}

    QPixmap MySlot::testDraw()
    {
    QPixmap pm(100,100);
    pm.fill();
    QPainter p(&pm);
    QPen pen(Qt::black, 10);
    p.setPen(pen);
    p.drawPoint(40,40);
    return pm;
    }

    int main(int argc, char *argv[])
    {
    QApplication application(argc, argv);
    QWidget window;
    MySlot myslot;
    QVBoxLayout* mainLayout = new QVBoxLayout(&window);
    QPushButton* button1 = new QPushButton("Draw");
    QLabel* pictureLabel = new QLabel;

    QPixmap pm;
    QObject::connect(button1, SIGNAL(clicked()), &myslot, SLOT(pm=testDraw()));
    pictureLabel->setPixmap(pm);

    mainLayout->addWidget(pictureLabel);
    mainLayout->addWidget(button1);
    window.show();
    return application.exec();
    }

  2. #2
    Join Date
    Jan 2006
    Location
    Germany
    Posts
    258
    Thanks
    22
    Thanked 19 Times in 16 Posts
    Qt products
    Qt4 Qt5
    Platforms
    MacOS X Unix/X11 Windows Android

    Default Re: slot control of new function

    Your code can't work, because the slot does not work on the pixmap it should. It creates a pixmap and returns it to nowhere. Slots should have void as return value. You should do your drawing in a QWidget derived class. Below I have put some code that do what you intended to do. I modified it a little to make it place the rectangle at a new random place every time you click on the draw button.

    Qt Code:
    1. #include <QApplication>
    2. #include <QtGui>
    3.  
    4. class MyWidget : public QWidget
    5. {
    6. Q_OBJECT
    7. public:
    8. MyWidget (QWidget* parent = 0);
    9.  
    10. public slots:
    11. void testDraw();
    12. private:
    13. QLabel* m_pixmapLabel;
    14. QPushButton* m_drawButton;
    15. };
    16.  
    17. MyWidget::MyWidget(QWidget* parent)
    18. : QWidget(parent)
    19. {
    20. setWindowTitle(tr("Drawing on pixmaps"));
    21.  
    22. m_pixmapLabel = new QLabel;
    23. m_drawButton = new QPushButton("&Draw");
    24. connect(m_drawButton, SIGNAL(clicked()), this, SLOT(testDraw()));
    25.  
    26. // Layout
    27. QVBoxLayout* mainLayout = new QVBoxLayout;
    28. mainLayout->addWidget(m_pixmapLabel);
    29. mainLayout->addWidget(m_drawButton);
    30. setLayout(mainLayout);
    31.  
    32. // to adjust window size
    33. testDraw();
    34. }
    35.  
    36. void MyWidget::testDraw()
    37. {
    38. QPixmap pm(400, 300);
    39. pm.fill();
    40. QPainter p(&pm);
    41. QPen pen(Qt::black, 10);
    42. p.setPen(pen);
    43. p.drawPoint(qrand()%390, qrand()%290);
    44. m_pixmapLabel->setPixmap(pm);
    45. }
    46.  
    47. #include "main.moc"
    48. int main(int argc, char *argv[])
    49. {
    50. QApplication application(argc, argv);
    51. MyWidget window;
    52. window.show();
    53. return application.exec();
    54. }
    To copy to clipboard, switch view to plain text mode 
    Last edited by momesana; 11th November 2007 at 01:43. Reason: adding code

  3. The following user says thank you to momesana for this useful post:

    tommy (11th November 2007)

  4. #3
    Join Date
    Nov 2007
    Posts
    103
    Thanks
    71
    Thanked 2 Times in 2 Posts
    Qt products
    Qt4
    Platforms
    Windows

    Default Re: slot control of new function

    Momesana, this is truly amazing. Thank you so much!!
    I had to remove #include "main.moc" in order to make this
    code to compile but it works like charm.
    What does #include "main.moc" do anyway?

  5. #4
    Join Date
    Jan 2006
    Location
    Germany
    Posts
    258
    Thanks
    22
    Thanked 19 Times in 16 Posts
    Qt products
    Qt4 Qt5
    Platforms
    MacOS X Unix/X11 Windows Android

    Default Re: slot control of new function

    You include main.moc from main.cpp if you have QObject based classes in it. You could have pasted the entire code into a file main.cpp and compiled the code without other files. This is helpful for testing since you don't need to mess around with many different files for small testing apps.
    #include "main.moc" tells the moc compiler that it should create the corresponding classes for the QObject derived classes in main.cpp.

    By the way, you could have made your example work without the new QWidget class by passing a pointer to the pixmap that is set in the QLabel to MySlot. The problem is that QLabel:ixmap() returns a pointer to a constant QPixmap but we need a non-const pointer. We also can't pass a pointer to the pixmap we originally created since it is not identical with the QLabels pixmal after we have called QLabel::setPixmap() (setPixmap() takes its arguments by value so the original pixmap is actually copied).

    We can overcome this problem by using const_cast. This is an ugly hack. I did it for fun and you can play around with the code but it is probably not even safe because of the const_cast. Something like const_cast should always be viewed with suspicion. The general idea with this code is to use a handler class that has a pointer to the object that needs to be handled.

    Qt Code:
    1. #include <QApplication>
    2. #include <QtGui>
    3.  
    4. class QObject;
    5. class QPixmap;
    6.  
    7. class MySlot : public QObject
    8. {
    9. Q_OBJECT
    10.  
    11. public:
    12. MySlot (QPixmap* pixmap, QObject *parent = 0);
    13.  
    14. public slots:
    15. void testDraw();
    16. private:
    17. QPixmap* m_pixmap;
    18. };
    19.  
    20.  
    21. MySlot::MySlot(QPixmap* pixmap, QObject *parent)
    22. : QObject(parent),
    23. m_pixmap(pixmap)
    24. {
    25. testDraw();
    26. }
    27.  
    28. void MySlot::testDraw()
    29. {
    30. m_pixmap->fill();
    31. QPainter p(m_pixmap);
    32. QPen pen(Qt::black, 10);
    33. p.setPen(pen);
    34. p.drawPoint(qrand()%390, qrand()%290);
    35. }
    36.  
    37. #include "main.moc"
    38. int main(int argc, char *argv[])
    39. {
    40. QApplication application(argc, argv);
    41. QWidget window;
    42. QVBoxLayout* mainLayout = new QVBoxLayout(&window);
    43. QPushButton* button1 = new QPushButton("Draw");
    44. QLabel* pictureLabel = new QLabel;
    45.  
    46. QPixmap pm(400,300);
    47. pictureLabel->setPixmap(pm);
    48. MySlot myslot(const_cast<QPixmap*>(pictureLabel->pixmap()));
    49. QObject::connect(button1, SIGNAL(clicked()), &myslot, SLOT(testDraw()));
    50. QObject::connect(button1, SIGNAL(clicked()), pictureLabel, SLOT(update()));
    51.  
    52. mainLayout->addWidget(pictureLabel);
    53. mainLayout->addWidget(button1);
    54. window.show();
    55. return application.exec();
    56. }
    To copy to clipboard, switch view to plain text mode 
    Last edited by momesana; 11th November 2007 at 04:20.

Similar Threads

  1. How to declare SLOT as a parameter to member function?
    By QPlace in forum Qt Programming
    Replies: 2
    Last Post: 17th July 2018, 00:41
  2. KDE/QWT doubt on debian sarge
    By hildebrand in forum KDE Forum
    Replies: 13
    Last Post: 25th April 2007, 06:13
  3. use qpsql
    By raphaelf in forum Installation and Deployment
    Replies: 34
    Last Post: 22nd August 2006, 12:52
  4. Qt 4.1.4 plugin QPSQL
    By jcr in forum Installation and Deployment
    Replies: 4
    Last Post: 22nd June 2006, 22:55
  5. I got two problems when I used static compiled library of QT4
    By qintm in forum Installation and Deployment
    Replies: 8
    Last Post: 20th April 2006, 08:52

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
Digia, Qt and their respective logos are trademarks of Digia Plc in Finland and/or other countries worldwide.