Part 5: Enhancing the statusbar

Part 5: Enhancing the statusbar


[<< Contents] [<< Prev] [Next >>]

Signals and slots

Using the Qt signal and slot mechanism we will enhance the statusbar to say where the user clicked on central display area. The Qt signal and slot mechanism makes it easy for application objects to communicate without implementation interdependencies. The concept is that objects can send signals containing event information which can be received by other objects using special functions known as slots. The signal/slot system fits well with the way Graphical User Interfaces are designed.

The Qt Graphics View framework used to create the central display widget provides many useful facilities including allowing us to detect where the user clicked. We will enhance our Scene class to detect where the user clicked which will then send a signal, and we will enhance our MainWindow class to detect this signal with a slot and to display the information on the statusbar.

Enhancing the Scene

To detect where the user clicked we will implement the mousePressEvent method which receives QGraphicsSceneMouseEvent events. To send the signal we must add the Q_OBJECT macro and add a signal method. Our signal method will be called "message" and will contain a text string. The Q_OBJECT macro inside the private section of the class declaration is used to enable Qt meta-object features such as dynamic properties, signals, and slots.

scene.h

Because we do not need the full definition of the QGraphicsSceneMouseEvent class in this header, we instead add just a forward declaration.

class QGraphicsSceneMouseEvent;

Add the Q_OBJECT macro inside the class definition.

  Q_OBJECT

Add the signal method and mousePressEvent method definitions.

signals:
  void  message( QString );                                  // info text message signal

protected:
  void  mousePressEvent( QGraphicsSceneMouseEvent* );        // receive mouse press events

scene.cpp

Include the QGraphicsSceneMouseEvent header file.

#include <QGraphicsSceneMouseEvent>

Add the mousePressEvent implementation. Here we use information supplied to us in the QGraphicsSceneMouseEvent to check it was the left button pressed and the position of the mouse pointer.

/********************************** mousePressEvent **********************************/

void  Scene::mousePressEvent( QGraphicsSceneMouseEvent* event )
{
  // only interested if left mouse button pressed
  if ( event->button() != Qt::LeftButton ) return;

  // emit informative message
  qreal  x = event->scenePos().x();
  qreal  y = event->scenePos().y();
  emit message( QString("Clicked at %1,%2").arg(x).arg(y) );
}

We do not need to provide the implementation for the signal method as the Qt meta-object compiler will do this for us (see later).

Enhancing the MainWindow

To receive the signal we must add the Q_OBJECT macro and add a slot method that we will call "showMessage".

mainwindow.h

Add the Q_OBJECT macro inside the class definition.

  Q_OBJECT

Add the slot method definition.

public slots:
  void showMessage( QString );        // show message on status bar

mainwindow.cpp

Inside the MainWindow constructor we need to connect our slot to the signal.

  // connect message signal from scene to showMessage slot
  connect( m_scene, SIGNAL(message(QString)), this, SLOT(showMessage(QString)) );

And add the slot implementation that will show the signal message text on the statusbar.

/************************************ showMessage ************************************/

void  MainWindow::showMessage( QString msg )
{
  // display message on main window status bar
  statusBar()->showMessage( msg );
}

Compile and run

If we were to compile our updated code now, we would see compilation errors such as "undefined reference to `vtable for MainWindow'" because to use the Qt meta-object features such as signals and slots, one needs also to use the Qt meta-object compiler (moc). To tell KDevelop to check where the moc is needed we will again open the QMake Manager that can be found on the righthand side of KDevelop, ensure the "src" subproject is selected, and from the context menu (right-clicking on "src") select "Run qmake".

The new code will now successfully compile when we attempt to "Rebuild project". Run the application and click on the white central area to see the statusbar update.


[<< Contents] [<< Prev] [Next >>]


Last updated 14-Apr-2008