This widget is one of several components. I need the cursor to change just on the widget itself and not on the entire application so the override cursor is not an option.
So I took your suggestion and implemented a custom event (with the code below), but the event is processed before returning back to qgraphicsview and same issue happens :-(
I even added the ability to change the viewport cursor from the view context menu, and the same thing happens . . . the set cursor and the change cursor event are happening before the qv mouse move event and when it returns to the mouse event, it sets the cursor to the original "unwanted" cursor.
#ifndef __EVENT_H__
#define __EVENT_H__
#include <QEvent>
#include <QCursor>
class SetCursorEvent
: public QEvent{
public:
SetCursorEvent
( const QCursor & cursor
) : QEvent( SetCursorEvent
::type() ),
m_cursor( cursor )
{}
virtual ~SetCursorEvent()
{}
{
return EventType;
}
{
return m_cursor;
}
private:
static QEvent::Type EventType;
};
#endif
#ifndef __EVENT_H__
#define __EVENT_H__
#include <QEvent>
#include <QCursor>
class SetCursorEvent : public QEvent
{
public:
SetCursorEvent( const QCursor & cursor )
: QEvent( SetCursorEvent::type() ),
m_cursor( cursor )
{}
virtual ~SetCursorEvent()
{}
static QEvent::Type type()
{
return EventType;
}
QCursor cursor() const
{
return m_cursor;
}
private:
static QEvent::Type EventType;
QCursor m_cursor;
};
#endif
To copy to clipboard, switch view to plain text mode
#ifndef __VIEW_H__
#define __VIEW_H__
#include "event.h"
#include <QDebug>
#include <QEvent>
#include <QGraphicsView>
{
Q_OBJECT
public:
{
setFrameStyle
( QFrame::NoFrame );
setHorizontalScrollBarPolicy( Qt::ScrollBarAlwaysOff );
setVerticalScrollBarPolicy( Qt::ScrollBarAlwaysOff );
}
protected:
bool viewportEvent
( QEvent * event
) {
if( QEvent::CursorChange == event
->type
() ) {
qDebug() << "Cursor Change:" << viewport()->cursor().shape();
}
else if( SetCursorEvent::type() == event->type() )
{
SetCursorEvent * e = static_cast<SetCursorEvent*>(event);
qDebug() << "SetCursorEvent:" << e->cursor().shape();
viewport()->setCursor( e->cursor() );
}
}
};
#endif
#ifndef __VIEW_H__
#define __VIEW_H__
#include "event.h"
#include <QDebug>
#include <QEvent>
#include <QGraphicsView>
class View : public QGraphicsView
{
Q_OBJECT
public:
View( QWidget* parent = 0 ) : QGraphicsView( parent )
{
setFrameStyle( QFrame::NoFrame );
setHorizontalScrollBarPolicy( Qt::ScrollBarAlwaysOff );
setVerticalScrollBarPolicy( Qt::ScrollBarAlwaysOff );
}
protected:
bool viewportEvent( QEvent * event )
{
if( QEvent::CursorChange == event->type() )
{
qDebug() << "Cursor Change:" << viewport()->cursor().shape();
}
else if( SetCursorEvent::type() == event->type() )
{
SetCursorEvent * e = static_cast<SetCursorEvent*>(event);
qDebug() << "SetCursorEvent:" << e->cursor().shape();
viewport()->setCursor( e->cursor() );
}
return QGraphicsView::viewportEvent(event);
}
};
#endif
To copy to clipboard, switch view to plain text mode
#include "event.h"
#include "window.h"
#include "view.h"
#include "item.h"
#include <QAction>
#include <QApplication>
#include <QGraphicsScene>
#include <QMenu>
QEvent::Type SetCursorEvent
::EventType = static_cast<QEvent
::Type>
(QEvent::registerEventType());
{
m_scene
->setBackgroundBrush
(QBrush(Qt
::black, Qt
::SolidPattern));
m_view = new View;
m_view->setScene(m_scene);
m_view->fitInView( m_scene->sceneRect() );
setCentralWidget(m_view);
m_view->setContextMenuPolicy( Qt::CustomContextMenu );
connect( m_view,
SIGNAL( customContextMenuRequested
(const QPoint &) ),
SLOT( viewContextMenu
(const QPoint &) ) );
m_view->viewport()->setCursor( Qt::CrossCursor );
}
Window::~Window()
{
}
void Window
::viewContextMenu( const QPoint & pt
) {
contextMenu.addAction( tr("Extract Item") );
contextMenu.addAction( tr("Change Cursor") );
act = contextMenu.exec( m_view->viewport()->mapToGlobal(pt) );
if( NULL != act )
{
switch( contextMenu.actions().indexOf(act) )
{
case 0:
{
Item *item = new Item;
item
->setRect
( QRectF( 0,
0,
100,
100 ) );
item
->setPen
( QPen(Qt
::green) );
item
->setBrush
( QBrush(Qt
::red) );
item->setPos( m_view->mapToScene(pt) );
item->setCursor( Qt::SizeAllCursor );
connect( item,
SIGNAL( requestContextMenu(const QPoint&,const QRectF&) ),
SLOT( extractContextMenu(const QPoint&,const QRectF&) ) );
m_scene->addItem(item);
m_view->setContextMenuPolicy( Qt::DefaultContextMenu );
m_view->viewport()->setCursor( Qt::ForbiddenCursor );
break;
}
case 1:
{
Qt::CursorShape shape;
if( m_view->viewport()->cursor().shape() == Qt::OpenHandCursor )
{
shape = Qt::CrossCursor;
}
else
{
shape = Qt::OpenHandCursor;
}
SetCursorEvent * e = new SetCursorEvent( shape );
//m_view->viewport()->setCursor( shape );
break;
}
}
}
}
void Window
::extractContextMenu( const QPoint & pt,
const QRectF & /*rect*/ ) {
Item *pGI = qobject_cast<Item*>(sender());
contextMenu.addAction( tr("Done") );
contextMenu.addAction( tr("Change Cursor") );
act = contextMenu.exec( pt );
if( NULL != act )
{
switch( contextMenu.actions().indexOf(act) )
{
case 0:
{
m_view->setContextMenuPolicy( Qt::CustomContextMenu );
m_view->scene()->removeItem( pGI );
delete pGI;
//m_view->viewport()->setCursor( Qt::CrossCursor );
SetCursorEvent * e = new SetCursorEvent( Qt::CrossCursor );
break;
}
case 1:
{
//m_view->viewport()->setCursor( Qt::WaitCursor );
SetCursorEvent * e = new SetCursorEvent( Qt::WaitCursor );
break;
}
}
}
}
#include "event.h"
#include "window.h"
#include "view.h"
#include "item.h"
#include <QAction>
#include <QApplication>
#include <QGraphicsScene>
#include <QMenu>
QEvent::Type SetCursorEvent::EventType =
static_cast<QEvent::Type>(QEvent::registerEventType());
Window::Window( QWidget * p )
: QMainWindow( p )
{
m_scene = new QGraphicsScene( 0, 0, 1000, 1000);
m_scene->setBackgroundBrush(QBrush(Qt::black, Qt::SolidPattern));
m_view = new View;
m_view->setScene(m_scene);
m_view->fitInView( m_scene->sceneRect() );
setCentralWidget(m_view);
m_view->setContextMenuPolicy( Qt::CustomContextMenu );
connect( m_view,
SIGNAL( customContextMenuRequested(const QPoint &) ),
SLOT( viewContextMenu(const QPoint &) ) );
m_view->viewport()->setCursor( Qt::CrossCursor );
}
Window::~Window()
{
}
void Window::viewContextMenu( const QPoint & pt )
{
QMenu contextMenu;
QAction * act;
contextMenu.addAction( tr("Extract Item") );
contextMenu.addAction( tr("Change Cursor") );
act = contextMenu.exec( m_view->viewport()->mapToGlobal(pt) );
if( NULL != act )
{
switch( contextMenu.actions().indexOf(act) )
{
case 0:
{
Item *item = new Item;
item->setRect( QRectF( 0, 0, 100, 100 ) );
item->setPen( QPen(Qt::green) );
item->setBrush( QBrush(Qt::red) );
item->setPos( m_view->mapToScene(pt) );
item->setCursor( Qt::SizeAllCursor );
item->setFlag( QGraphicsItem::ItemIsMovable, true );
connect( item,
SIGNAL( requestContextMenu(const QPoint&,const QRectF&) ),
SLOT( extractContextMenu(const QPoint&,const QRectF&) ) );
m_scene->addItem(item);
m_view->setContextMenuPolicy( Qt::DefaultContextMenu );
m_view->viewport()->setCursor( Qt::ForbiddenCursor );
break;
}
case 1:
{
Qt::CursorShape shape;
if( m_view->viewport()->cursor().shape() == Qt::OpenHandCursor )
{
shape = Qt::CrossCursor;
}
else
{
shape = Qt::OpenHandCursor;
}
SetCursorEvent * e = new SetCursorEvent( shape );
QApplication::postEvent( m_view->viewport(), e );
//m_view->viewport()->setCursor( shape );
break;
}
}
}
}
void Window::extractContextMenu( const QPoint & pt, const QRectF & /*rect*/ )
{
QMenu contextMenu;
QAction * act;
Item *pGI = qobject_cast<Item*>(sender());
contextMenu.addAction( tr("Done") );
contextMenu.addAction( tr("Change Cursor") );
act = contextMenu.exec( pt );
if( NULL != act )
{
switch( contextMenu.actions().indexOf(act) )
{
case 0:
{
m_view->setContextMenuPolicy( Qt::CustomContextMenu );
m_view->scene()->removeItem( pGI );
delete pGI;
//m_view->viewport()->setCursor( Qt::CrossCursor );
SetCursorEvent * e = new SetCursorEvent( Qt::CrossCursor );
QApplication::postEvent( m_view->viewport(), e );
break;
}
case 1:
{
//m_view->viewport()->setCursor( Qt::WaitCursor );
SetCursorEvent * e = new SetCursorEvent( Qt::WaitCursor );
QApplication::postEvent( m_view->viewport(), e );
break;
}
}
}
}
To copy to clipboard, switch view to plain text mode
Bookmarks