Commit 71715e6b authored by Alexander Wiebel's avatar Alexander Wiebel
Browse files

[FIX] roi boxes should behave nicely now

parent 7a8f48dd
......@@ -55,7 +55,7 @@ public:
* \param pixelCoords pixel coordinates fo the mouse
* \param modKey relevant modifier key pressed during the pick
*/
inline WPickInfo( std::string name, wmath::WPosition pickPosition, std::pair< int, int > pixelCoords, modifierKey modKey );
inline WPickInfo( std::string name, wmath::WPosition pickPosition, std::pair< float, float > pixelCoords, modifierKey modKey );
/**
* Creates an object with the empty name, zero position and no modkey.
......@@ -80,7 +80,7 @@ public:
/**
* Get pixel coordinates where object was hit.
*/
inline std::pair< int, int > getPickPixelPosition();
inline std::pair< float, float > getPickPixelPosition();
/**
* Tests two pick infos for equality
......@@ -99,11 +99,11 @@ private:
std::string m_name; //!< name of picked object.
wmath::WPosition m_pickPosition; //!< position where object was hit.
std::pair< int, int > m_pixelCoords; //!< Pixel coordinates of the mouse.
std::pair< float, float > m_pixelCoords; //!< Pixel coordinates of the mouse.
modifierKey m_modKey; //!< modifier key associated with the pick
};
WPickInfo::WPickInfo( std::string name, wmath::WPosition pickPosition, std::pair< int, int > pixelCoords, modifierKey modKey ) :
WPickInfo::WPickInfo( std::string name, wmath::WPosition pickPosition, std::pair< float, float > pixelCoords, modifierKey modKey ) :
m_name( name ),
m_pickPosition( pickPosition ),
m_pixelCoords( pixelCoords ),
......@@ -134,7 +134,7 @@ wmath::WPosition WPickInfo::getPickPosition()
return m_pickPosition;
}
std::pair< int, int > WPickInfo::getPickPixelPosition()
std::pair< float, float > WPickInfo::getPickPixelPosition()
{
return m_pixelCoords;
}
......
......@@ -23,10 +23,13 @@
//---------------------------------------------------------------------------
#include <string>
#include <utility>
#include <osg/LineWidth>
#include <osg/LightModel>
#include <GL/glu.h>
#include "WROIBox.h"
#include "WGraphicsEngine.h"
......@@ -109,7 +112,9 @@ void setVertices( osg::Vec3Array* vertices, wmath::WPosition minPos, wmath::WPos
}
WROIBox::WROIBox( wmath::WPosition minPos, wmath::WPosition maxPos ) :
WROI(), boxId( maxBoxId++ )
WROI(),
boxId( maxBoxId++ ),
m_oldPixelPosition( std::make_pair( 0, 0 ) )
{
m_minPos = minPos;
m_maxPos = maxPos;
......@@ -118,7 +123,8 @@ WROIBox::WROIBox( wmath::WPosition minPos, wmath::WPosition maxPos ) :
assert( ge );
boost::shared_ptr< WGEViewer > viewer = ge->getViewerByName( "main" );
assert( viewer );
m_pickHandler = viewer->getPickHandler();
m_viewer = viewer;
m_pickHandler = m_viewer->getPickHandler();
m_pickHandler->getPickSignal()->connect( boost::bind( &WROIBox::registerRedrawRequest, this, _1 ) );
osg::Geometry* surfaceGeometry = new osg::Geometry();
......@@ -210,25 +216,27 @@ void WROIBox::updateGFX()
ss << "ROIBox" << boxId << "";
if ( m_pickInfo.getName() == ss.str() )
{
// connect updateGFX with picking
boost::shared_ptr< WGraphicsEngine > ge = WGraphicsEngine::getGraphicsEngine();
assert( ge );
boost::shared_ptr< WGEViewer > viewer = ge->getViewerByName( "main" );
assert( viewer );
wmath::WPosition newPos( m_pickInfo.getPickPosition() );
std::pair< float, float > newPixelPos( m_pickInfo.getPickPixelPosition() );
if ( m_isPicked )
{
osg::Vec3d eyeDirOSG = osg::Matrix::transform3x3( osg::Vec3d( 0, 0, -1 ),
osg::Matrix::inverse( viewer->getCamera()->getViewMatrix() ) );
wmath::WVector3D eyeDir( eyeDirOSG[0], eyeDirOSG[1], eyeDirOSG[2] );
eyeDir.normalize();
wmath::WVector3D moveVec = newPos - m_pickedPosition;
// moveVec = moveVec - eyeDir * ( moveVec * eyeDir );
osg::Vec3 in( newPixelPos.first, newPixelPos.second, 0.0 );
osg::Vec3 world = unprojectFromScreen( in );
wmath::WPosition newPixelWorldPos( world[0], world[1], world[2] );
wmath::WPosition oldPixelWorldPos;
if( m_oldPixelPosition.first == 0 && m_oldPixelPosition.second == 0 )
{
oldPixelWorldPos = newPixelWorldPos;
}
else
{
osg::Vec3 in( m_oldPixelPosition.first, m_oldPixelPosition.second, 0.0 );
osg::Vec3 world= unprojectFromScreen( in );
oldPixelWorldPos = wmath::WPosition( world[0], world[1], world[2] );
}
wmath::WVector3D moveVec = newPixelWorldPos - oldPixelWorldPos;
osg::Vec3Array* vertices = new osg::Vec3Array;
m_minPos += moveVec;
......@@ -243,6 +251,7 @@ void WROIBox::updateGFX()
( ( osg::Geometry* ) ( m_geode->getDrawable( 0 ) ) )->setColorArray( colors );
}
m_pickedPosition = newPos;
m_oldPixelPosition = newPixelPos;
m_isModified = true;
m_isPicked = true;
......@@ -258,3 +267,33 @@ void WROIBox::updateGFX()
lock.unlock();
}
osg::Vec3 WROIBox::unprojectFromScreen( const osg::Vec3 screen )
{
double* modelView;
double* projection;
double dviewport[4];
modelView = m_viewer->getCamera()->getViewMatrix().ptr();
projection = m_viewer->getCamera()->getProjectionMatrix().ptr();
dviewport[0] = m_viewer->getCamera()->getViewport()->x();
dviewport[1] = m_viewer->getCamera()->getViewport()->y();
dviewport[2] = m_viewer->getCamera()->getViewport()->width();
dviewport[3] = m_viewer->getCamera()->getViewport()->height();
double x, y, z;
GLint viewport[4];
viewport[0] = static_cast< GLint >( dviewport[0] );
viewport[1] = static_cast< GLint >( dviewport[1] );
viewport[2] = static_cast< GLint >( dviewport[2] );
viewport[3] = static_cast< GLint >( dviewport[3] );
gluUnProject( screen[0], screen[1], screen[2], modelView, projection, viewport, &x, &y, &z );
osg::Vec3 world;
world[0] = x;
world[1] = y;
world[2] = z;
return world;
}
......@@ -26,11 +26,13 @@
#define WROIBOX_H
#include <string>
#include <utility>
#include <boost/thread.hpp>
#include "../math/WPosition.h"
#include "WPickHandler.h"
#include "WGEViewer.h"
#include "WROI.h"
......@@ -71,10 +73,13 @@ private:
wmath::WPosition m_maxPos; //!< The maximum position of the box
bool m_isPicked; //!< Indicates whether the box is currently picked or not.
wmath::WPosition m_pickedPosition; //!< Caches the old picked position to a allow for cmoparison
std::pair< float, float > m_oldPixelPosition; //!< Caches the old picked position to a allow for cmoparison
boost::shared_mutex m_updateLock; //!< Lock to prevent concurrent threads trying to update the osg node
WPickInfo m_pickInfo; //!< Stores the pick information for potential redraw
boost::shared_ptr< WGEViewer > m_viewer; //!< makes viewer available all over this class.
/**
* note that there was a pick
* \param pickInfo info from pick
......@@ -86,6 +91,13 @@ private:
*/
virtual void updateGFX();
/**
* Get wordl coordinates from screen coordinates.
* \return the world coordinates.
* \param screen the screen coordinates in pixels and z depth.
*/
osg::Vec3 unprojectFromScreen( const osg::Vec3 screen );
/**
* Node callback to handle updates properly
*/
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment