fw4spl
Scene2DGraphicsView.cpp
1 /* ***** BEGIN LICENSE BLOCK *****
2  * FW4SPL - Copyright (C) IRCAD, 2009-2017.
3  * Distributed under the terms of the GNU Lesser General Public License (LGPL) as
4  * published by the Free Software Foundation.
5  * ****** END LICENSE BLOCK ****** */
6 
7 #include "fwRenderQt/Scene2DGraphicsView.hpp"
8 
9 #include "fwRenderQt/data/Size.hpp"
10 #include "fwRenderQt/SRender.hpp"
11 
12 #include <QMouseEvent>
13 
14 namespace fwRenderQt
15 {
16 
17 //-----------------------------------------------------------------------------
18 
19 Scene2DGraphicsView::Scene2DGraphicsView(QGraphicsScene* scene, QWidget* widget) :
20  QGraphicsView(scene, widget)
21 {
22  if( !this->hasMouseTracking() )
23  {
24  this->setMouseTracking( true );
25  }
26 
27  /* Change the method used by the scene to index its items:
28  * 'NoIndex' is better than the default method 'BspTreeIndex' (Binary Space Partioning)
29  * which consists in dividing the scene into multiple parts and store them into a tree.
30  * With 'NoIndex', searching an item is faster, especially for scenes with a lot of items
31  * (Histogram for instance) and for scenes which manage moves (ViewportRangeSelector and
32  * ViewportUpdater for instance).
33  */
34  scene->setItemIndexMethod( QGraphicsScene::NoIndex );
35 
36  this->setVerticalScrollBarPolicy( Qt::ScrollBarAlwaysOff );
37  this->setHorizontalScrollBarPolicy( Qt::ScrollBarAlwaysOff );
38 
39  this->setViewportUpdateMode( QGraphicsView::BoundingRectViewportUpdate );
40  this->setOptimizationFlags( QGraphicsView::DontSavePainterState
41  | QGraphicsView::DontAdjustForAntialiasing ); // Prevent from rendering artifacts
42  this->setCacheMode( QGraphicsView::CacheBackground ); // Activates background cache
43  this->setAttribute( Qt::WA_TranslucentBackground, false );
44  this->setFrameStyle( 0 );
45 }
46 
47 //-----------------------------------------------------------------------------
48 
49 void Scene2DGraphicsView::setSceneRender( ::fwRenderQt::SRender::sptr sceneRender )
50 {
51  m_scene2DRender = sceneRender;
52 }
53 
54 //-----------------------------------------------------------------------------
55 
56 void Scene2DGraphicsView::keyPressEvent(QKeyEvent* _event)
57 {
58  ::fwRenderQt::data::Event sceneEvent;
59  sceneEvent.setType( ::fwRenderQt::data::Event::KeyPress);
60  sceneEvent.setButton( ::fwRenderQt::data::Event::NoButton);
61  sceneEvent.setModifier( this->getScene2DModifierFromEvent( _event) );
62  sceneEvent.setKey(_event->key());
63 
64  m_scene2DRender.lock()->dispatchInteraction( sceneEvent );
65 }
66 
67 //-----------------------------------------------------------------------------
68 
69 void Scene2DGraphicsView::keyReleaseEvent(QKeyEvent* _event)
70 {
71  ::fwRenderQt::data::Event sceneEvent;
72  sceneEvent.setType( ::fwRenderQt::data::Event::KeyRelease);
73  sceneEvent.setButton( ::fwRenderQt::data::Event::NoButton);
74  sceneEvent.setModifier( this->getScene2DModifierFromEvent( _event) );
75  sceneEvent.setKey(_event->key());
76 
77  m_scene2DRender.lock()->dispatchInteraction( sceneEvent );
78 }
79 
80 //-----------------------------------------------------------------------------
81 
82 void Scene2DGraphicsView::resizeEvent(QResizeEvent* _event)
83 {
84  this->updateFromViewport();
85 
86  ::fwRenderQt::data::Event sceneEvent;
87  sceneEvent.setType( ::fwRenderQt::data::Event::Resize);
88  sceneEvent.setButton( ::fwRenderQt::data::Event::NoButton);
89  sceneEvent.setModifier( ::fwRenderQt::data::Event::NoModifier);
90  sceneEvent.setSize( ::fwRenderQt::data::Size( _event->size().width(), _event->size().height() ) );
91  sceneEvent.setOldSize( ::fwRenderQt::data::Size( _event->oldSize().width(), _event->oldSize().height() ) );
92 
93  m_scene2DRender.lock()->dispatchInteraction( sceneEvent );
94 }
95 
96 //-----------------------------------------------------------------------------
97 
98 void Scene2DGraphicsView::mousePressEvent ( QMouseEvent* _event )
99 {
100  OSLM_TRACE("Press in x = " << _event->localPos().x() << " y = " << _event->localPos().y() );
101 
102  ::fwRenderQt::data::Event sceneEvent;
103  sceneEvent.setType( ::fwRenderQt::data::Event::MouseButtonPress );
104  sceneEvent.setCoord( ::fwRenderQt::data::Coord( _event->localPos().x(), _event->localPos().y() ) );
105  sceneEvent.setButton( this->getScene2DButtonFromEvent( _event ) );
106  sceneEvent.setModifier( this->getScene2DModifierFromEvent( _event) );
107 
108  m_scene2DRender.lock()->dispatchInteraction( sceneEvent );
109 }
110 
111 //-----------------------------------------------------------------------------
112 
113 ::fwRenderQt::data::Event::Modifier Scene2DGraphicsView::getScene2DModifierFromEvent( QInputEvent* _event )
114 {
115  ::fwRenderQt::data::Event::Modifier modifier;
116 
117  if(_event->modifiers() == Qt::ControlModifier)
118  {
119  modifier = ::fwRenderQt::data::Event::ControlModifier;
120  }
121  else if(_event->modifiers() == Qt::AltModifier)
122  {
123  modifier = ::fwRenderQt::data::Event::AltModifier;
124  }
125  else if(_event->modifiers() == Qt::ShiftModifier)
126  {
127  modifier = ::fwRenderQt::data::Event::ShiftModifier;
128  }
129  else
130  {
131  modifier = ::fwRenderQt::data::Event::NoModifier;
132  }
133 
134  // TODO: add support for combined modifiers
135  return modifier;
136 }
137 
138 //-----------------------------------------------------------------------------
139 
140 ::fwRenderQt::data::Event::Button Scene2DGraphicsView::getScene2DButtonFromEvent( QMouseEvent* _event )
141 {
142  ::fwRenderQt::data::Event::Button button;
143 
144  if( _event->button() == Qt::LeftButton )
145  {
146  button = ::fwRenderQt::data::Event::LeftButton;
147  }
148  else if( _event->button() == Qt::RightButton )
149  {
150  button = ::fwRenderQt::data::Event::RightButton;
151  }
152  else if( _event->button() == Qt::MidButton )
153  {
154  button = ::fwRenderQt::data::Event::MidButton;
155  }
156  else
157  {
158  button = ::fwRenderQt::data::Event::NoButton;
159  }
160 
161  return button;
162 }
163 
164 //-----------------------------------------------------------------------------
165 
166 void Scene2DGraphicsView::mouseDoubleClickEvent ( QMouseEvent* _event )
167 {
168  OSLM_TRACE("DoubleClick in x = " << _event->localPos().x() << " y = " << _event->localPos().y() );
169 
170  ::fwRenderQt::data::Event sceneEvent;
171  sceneEvent.setType( ::fwRenderQt::data::Event::MouseButtonDoubleClick );
172  sceneEvent.setCoord( ::fwRenderQt::data::Coord( _event->localPos().x(), _event->localPos().y() ) );
173  sceneEvent.setButton( this->getScene2DButtonFromEvent( _event ) );
174  sceneEvent.setModifier( this->getScene2DModifierFromEvent( _event) );
175 
176  m_scene2DRender.lock()->dispatchInteraction( sceneEvent );
177 }
178 
179 //-----------------------------------------------------------------------------
180 
181 void Scene2DGraphicsView::mouseReleaseEvent ( QMouseEvent* _event )
182 {
183  OSLM_TRACE("Release in x = " << _event->localPos().x() << " y = " << _event->localPos().y() );
184  ::fwRenderQt::data::Event sceneEvent;
185  sceneEvent.setType( ::fwRenderQt::data::Event::MouseButtonRelease );
186  sceneEvent.setCoord( ::fwRenderQt::data::Coord( _event->localPos().x(), _event->localPos().y() ) );
187  sceneEvent.setButton( this->getScene2DButtonFromEvent( _event ) );
188  sceneEvent.setModifier( this->getScene2DModifierFromEvent( _event) );
189 
190  m_scene2DRender.lock()->dispatchInteraction( sceneEvent );
191 }
192 
193 //-----------------------------------------------------------------------------
194 
195 void Scene2DGraphicsView::mouseMoveEvent ( QMouseEvent* _event )
196 {
197  OSLM_TRACE("Move in x = " << _event->localPos().x() << " y = " << _event->localPos().y() );
198  ::fwRenderQt::data::Event sceneEvent;
199  sceneEvent.setType( ::fwRenderQt::data::Event::MouseMove );
200  sceneEvent.setCoord( ::fwRenderQt::data::Coord( _event->localPos().x(), _event->localPos().y() ) );
201  sceneEvent.setButton( this->getScene2DButtonFromEvent( _event ) );
202  sceneEvent.setModifier( this->getScene2DModifierFromEvent( _event) );
203 
204  m_scene2DRender.lock()->dispatchInteraction( sceneEvent );
205 }
206 
207 //-----------------------------------------------------------------------------
208 
209 void Scene2DGraphicsView::wheelEvent ( QWheelEvent* _event )
210 {
211  const bool scrollUp = _event->delta() > 0;
212  OSLM_TRACE("Scroll " << (scrollUp ? "up" : "down") << " _event");
213  ::fwRenderQt::data::Event sceneEvent;
214  sceneEvent.setType( (scrollUp) ? ::fwRenderQt::data::Event::MouseWheelUp : ::fwRenderQt::data::Event::MouseWheelDown);
215  sceneEvent.setCoord( ::fwRenderQt::data::Coord( _event->pos().x(), _event->pos().y() ) );
216  sceneEvent.setModifier( this->getScene2DModifierFromEvent( _event) );
217 
218  m_scene2DRender.lock()->dispatchInteraction( sceneEvent );
219 }
220 
221 //-----------------------------------------------------------------------------
222 
223 void Scene2DGraphicsView::setViewport( ::fwRenderQt::data::Viewport::sptr viewport )
224 {
225  m_viewport = viewport;
226 }
227 
228 //-----------------------------------------------------------------------------
229 
230 void Scene2DGraphicsView::updateFromViewport()
231 {
232  SLM_ASSERT("Viewport is not set", m_viewport);
233 
234  this->fitInView(m_viewport->getX(), m_viewport->getY(),
235  m_viewport->getWidth(), m_viewport->getHeight(),
236  m_scene2DRender.lock()->getAspectRatioMode() );
237 }
238 
239 //-----------------------------------------------------------------------------
240 
241 void Scene2DGraphicsView::paintEvent(QPaintEvent* event)
242 {
243  // QGraphicsView optimization
244  QPaintEvent* newEvent = new QPaintEvent( event->region().boundingRect() );
245  QGraphicsView::paintEvent(newEvent);
246 
247  delete newEvent;
248 }
249 
250 //-----------------------------------------------------------------------------
251 
252 } // namespace fwRenderQt
253 
#define OSLM_TRACE(message)
Definition: spyLog.hpp:230
#define SLM_ASSERT(message, cond)
work like &#39;assert&#39; from &#39;cassert&#39;, with in addition a message logged by spylog (with FATAL loglevel) ...
Definition: spyLog.hpp:308
The namespace fwRenderQt contains classes for rendering with Qt.
Definition: Axis.hpp:12
This class manage events on the scene 2D (mouse event, keyboard event , ...).
Definition: Event.hpp:26