PDA

View Full Version : Can not capture expected mouse move event from GraphicsItem::sceneEventFilter



chiaminhsu
26th April 2013, 04:13
Hi Qt experts,

I can not capture the expected mouse move event from GraphicsItem::sceneEvent().

I rewrite David w drell's code of "Example of re-sizing a QGraphicsItem using Mouse events." (http://www.davidwdrell.net/wordpress/?page_id=46)

The class StateBox inherits from QGraphicsPixmapItem and install the corner members that users can drag the corner to to-size the item.

These corners have been installed and sceneEventFilter() watch them.

class Corner : public QGraphicsItem {..}
class StateBox : public QGraphicsPixmapItem { .. Corner* _corners[8]; ..};

void StateBox::hoverEnterEvent(QGraphicsSceneHoverEvent *) {
.. _corners[i]->installSceneEventFilter(this); ..} // then item can watch corner event


in the event watch filter - sceneEventFilter(QGraphicsItem *watched, QEvent* event),
I monitor the mouse movement of the corner in the StateBox's coordinate

Corner *corner = dynamic_cast<Corner*>(watched);
...
QGraphicsSceneMouseEvent * mevent
= dynamic_cast<QGraphicsSceneMouseEvent*>(event);

if (event->type() == QEvent::GraphicsSceneMouseMove)
// dump mevemt->pos();

However, the mouse movement is very strange ..
If I drag the bottom-right corner, the position seems located on StateBox's coordinate and corner's coordinate.

Is it a normal behavior ?

How can I get the corner's position always in StateBox's ?

this is my code link
StateBox (http://ideone.com/zfwpQN) StateBox (http://ideone.com/zqgifY)

this is the mouse moving data form corner 2 (the right-bottom corner)
8990
" QEvent == 156" corner 2 mousedown QPointF(1, 3) // ? corner' coordinate ?
" QEvent == 155" corner 2 move QPointF(2, 3) // ? corner's coordinate ?
" QEvent == 155" corner 2 move QPointF(88, 89) // statebox's coordinate
" QEvent == 155" corner 2 move QPointF(4, 4) // ? corner's coordinate ?
" QEvent == 155" corner 2 move QPointF(90, 90) // statebox's coordinate
" QEvent == 155" corner 2 move QPointF(6, 7)
" QEvent == 155" corner 2 move QPointF(91, 91)
" QEvent == 155" corner 2 move QPointF(8, 8)
" QEvent == 155" corner 2 move QPointF(93, 92)

Can you help ? Thank you very much.

d_stranz
27th April 2013, 00:49
If the Corner instance is a child of StateBox (in other words, when you create the Corner instance, you set its parent to the StateBox instance), then you can use corner->mapToParent( mevent->pos() ) to get the mouse position in StateBox coordinates.

But you have to check to be sure it is the Corner instance that is sending the event, and not the StateBox. In the list of events you posted, some are from a Corner, some are from the StateBox. To make sure of this, do not use dynamic_cast<> use qgraphicsitem_cast< Corner >( watched ); It will return 0 if the object is not a Corner. To make this work, you must reimplement the QGraphicsItem::type() method for your Corner class.

chiaminhsu
27th April 2013, 05:40
Hi,

I modify the code as you said


// overwrite virtual function type() in CornerGrabber
enum { Type = UserType + 1101; } // just some number
virtual int type() const { return Type; }

// in sceneEventFilter()
CornerGrabber * corner = qgraphicsitem_cast<CornerGrabber *>(watched);
QPointF p = corner->mapToParent(mevent->pos());

It works! Thank you very much :D