Commit 476081cc authored by Sebastian Eichelbaum's avatar Sebastian Eichelbaum

[ADD #59] first things needed for saving ROIs in project files. Saving now...

[ADD #59] first things needed for saving ROIs in project files. Saving now works but loading does not. Also added some WORKING lighting for ROI boxes.
parent a2f66019
......@@ -77,3 +77,41 @@ void WProjectFileIO::addWarning( std::string description )
m_warnings.push_back( description );
}
void WProjectFileIO::printProperties( std::ostream& output, boost::shared_ptr< WProperties > props, std::string indent, //NOLINT
std::string prefix, unsigned int index, std::string indexPrefix )
{
// lock, unlocked if l looses focus
WProperties::PropertySharedContainerType::ReadTicket l = props->getProperties();
output << indent << "// Property Group: " << props->getName() << std::endl;
// iterate of them and print them to output
for( WProperties::PropertyConstIterator iter = l->get().begin(); iter != l->get().end(); ++iter )
{
// information properties do not get written
if( ( *iter )->getPurpose () == PV_PURPOSE_INFORMATION )
{
continue;
}
if( ( *iter )->getType() != PV_GROUP )
{
output << indent + " " << "PROPERTY:(" << indexPrefix << index << "," << prefix + ( *iter )->getName() << ")="
<< ( *iter )->getAsString() << std::endl;
}
else
{
// it is a group -> recursively print it
if( prefix.empty() )
{
printProperties( output, ( *iter )->toPropGroup(), indent + " ", ( *iter )->getName() + "/", index, indexPrefix );
}
else
{
printProperties( output, ( *iter )->toPropGroup(), indent + " ", prefix + ( *iter )->getName() + "/", index, indexPrefix );
}
}
}
output << indent << "// Property Group END: " << props->getName() << std::endl;
}
......@@ -29,6 +29,8 @@
#include <string>
#include <vector>
#include "WProperties.h"
/**
* A base class for all parts of OpenWalnut which can be serialized to a project file. It is used by WProjectFile to actually parse the file line
* by line. Derive from this class if you write your own parser and use it to fill your internal data structures. But write it in a very
......@@ -117,6 +119,18 @@ protected:
*/
void addWarning( std::string description );
/**
* Recursively prints the properties and nested properties.
*
* \param output the output stream to print to
* \param props the properties to recursively print
* \param indent the indentation level
* \param prefix the prefix (name prefix of property)
* \param index the ID to use
* \param indexPrefix use this to add a prefix to the index
*/
void printProperties( std::ostream& output, boost::shared_ptr< WProperties > props, std::string indent, //NOLINT ( non-const ref )
std::string prefix, unsigned int index, std::string indexPrefix = "" );
private:
/**
* List of errors if any.
......
......@@ -31,6 +31,7 @@
#include <osg/Geometry>
#include "../common/WLogger.h"
#include "shaders/WGEShader.h"
#include "WROIBox.h"
#include "WGraphicsEngine.h"
......@@ -120,11 +121,14 @@ WROIBox::WROIBox( WPosition minPos, WPosition maxPos ) :
m_pickNormal( WVector3d() ),
m_oldPixelPosition( WVector2d::zero() ),
m_oldScrollWheel( 0 ),
m_color( osg::Vec4( 0.f, 1.f, 1.f, 0.4f ) ),
m_notColor( osg::Vec4( 1.0f, 0.0f, 0.0f, 0.4f ) )
m_color( osg::Vec4( 0.391f, 0.594f, 0.828f, 0.5f ) ),
m_notColor( osg::Vec4( 0.828f, 0.391f, 0.391f, 0.5f ) )
{
m_minPos = minPos;
m_maxPos = maxPos;
m_propGrp = m_properties->addPropertyGroup( "ROI Box", "Properties of this ROI Box" );
m_minPos = m_propGrp->addProperty( "Min Position", "When a box is described by its diagonal, this is the lower, left, front corner of it.",
minPos, boost::bind( &WROIBox::boxPropertiesChanged, this, _1 ) );
m_maxPos = m_propGrp->addProperty( "Max Position", "When a box is described by its diagonal, this is the upper, right, back corner of it.",
maxPos, boost::bind( &WROIBox::boxPropertiesChanged, this, _1 ) );
boost::shared_ptr< WGraphicsEngine > ge = WGraphicsEngine::getGraphicsEngine();
assert( ge );
......@@ -178,6 +182,9 @@ WROIBox::WROIBox( WPosition minPos, WPosition maxPos ) :
state->setAttributeAndModes( lightModel.get(), osg::StateAttribute::ON );
state->setMode( GL_BLEND, osg::StateAttribute::ON );
// add a simple default lighting shader
m_lightShader = new WGEShader( "WGELighting" );
m_not->set( false );
assert( WGraphicsEngine::getGraphicsEngine() );
......@@ -195,10 +202,20 @@ WROIBox::~WROIBox()
WPosition WROIBox::getMinPos() const
{
return m_minPos;
return m_minPos->get();
}
WPosition WROIBox::getMaxPos() const
{
return m_maxPos->get();
}
WPropPosition WROIBox::getMinPosProperty()
{
return m_minPos;
}
WPropPosition WROIBox::getMaxPosProperty()
{
return m_maxPos;
}
......@@ -213,6 +230,13 @@ void WROIBox::registerRedrawRequest( WPickInfo pickInfo )
lock.unlock();
}
void WROIBox::boxPropertiesChanged( boost::shared_ptr< WPropertyBase > /* property */ )
{
m_needVertexUpdate = true;
// NOTE: this is probably not needed as the above flag will trigger a dirty
// setDirty();
}
void WROIBox::updateGFX()
{
boost::unique_lock< boost::shared_mutex > lock;
......@@ -251,34 +275,26 @@ void WROIBox::updateGFX()
WVector3d moveVec = newPixelWorldPos - oldPixelWorldPos;
osg::ref_ptr<osg::Vec3Array> vertices = osg::ref_ptr<osg::Vec3Array>( new osg::Vec3Array );
// resize Box
if( m_pickInfo.getModifierKey() == WPickInfo::SHIFT )
{
if( m_pickNormal[0] <= 0 && m_pickNormal[1] <= 0 && m_pickNormal[2] <= 0 )
{
m_maxPos += m_pickNormal * dot( moveVec, m_pickNormal );
m_maxPos->set( m_maxPos->get() + ( m_pickNormal * dot( moveVec, m_pickNormal ) ) );
}
if( m_pickNormal[0] >= 0 && m_pickNormal[1] >= 0 && m_pickNormal[2] >= 0 )
{
m_minPos += m_pickNormal * dot( moveVec, m_pickNormal );
m_minPos->set( m_minPos->get() + ( m_pickNormal * dot( moveVec, m_pickNormal ) ) );
}
setVertices( vertices, m_minPos, m_maxPos );
m_surfaceGeometry->setVertexArray( vertices );
// NOTE: this sets m_needVertexUpdate
}
// move Box
if( m_pickInfo.getModifierKey() == WPickInfo::NONE )
{
m_minPos += moveVec;
m_maxPos += moveVec;
m_minPos += 2.0 * toDepthWorld * depthMove;
m_maxPos += 2.0 * toDepthWorld * depthMove;
setVertices( vertices, m_minPos, m_maxPos );
m_surfaceGeometry->setVertexArray( vertices );
m_minPos->set( m_minPos->get() + moveVec + ( 2.0 * toDepthWorld * depthMove ) );
m_maxPos->set( m_maxPos->get() + moveVec + ( 2.0 * toDepthWorld * depthMove ) );
// NOTE: this sets m_needVertexUpdate
}
}
else
......@@ -311,8 +327,6 @@ void WROIBox::updateGFX()
setDirty();
m_isPicked = true;
m_oldScrollWheel = m_pickInfo.getScrollWheel();
signalRoiChange();
}
if( m_isPicked && m_pickInfo.getName() == "unpick" )
{
......@@ -332,6 +346,18 @@ void WROIBox::updateGFX()
m_isPicked = false;
}
if( m_needVertexUpdate )
{
osg::ref_ptr<osg::Vec3Array> vertices = osg::ref_ptr<osg::Vec3Array>( new osg::Vec3Array );
setVertices( vertices, m_minPos->get(), m_maxPos->get() );
m_surfaceGeometry->setVertexArray( vertices );
m_lightShader->apply( this );
setDirty();
m_needVertexUpdate = false;
}
if( m_dirty->get() )
{
osg::ref_ptr<osg::Vec4Array> colors = osg::ref_ptr<osg::Vec4Array>( new osg::Vec4Array );
......
......@@ -33,11 +33,12 @@
#include <osg/Geometry>
#include "WPickHandler.h"
#include "shaders/WGEShader.h"
class WGEViewer;
#include "WROI.h"
/**
* A box representing a region of interest.
*/
......@@ -67,6 +68,20 @@ public:
*/
WPosition getMaxPos() const;
/**
* Get the corner of the box that has minimal x, y and z values
*
* \return the corner position
*/
WPropPosition getMinPosProperty();
/**
* Get the corner of the box that has maximal x, y and z values
*
* \return the corner position
*/
WPropPosition getMaxPosProperty();
/**
* Setter for standard color
* \param color The new color.
......@@ -84,8 +99,22 @@ private:
static size_t maxBoxId; //!< Current maximum boxId over all boxes.
size_t boxId; //!< Id of the current box.
WPosition m_minPos; //!< The minimum position of the box
WPosition m_maxPos; //!< The maximum position of the box
/**
* Group for box specific props
*/
WPropGroup m_propGrp;
WPropPosition m_minPos; //!< The minimum position of the box
WPropPosition m_maxPos; //!< The maximum position of the box
/**
* Shader for proper lighting.
*/
WGEShader::RefPtr m_lightShader;
/**
* If true, the box' vertex data is updated.
*/
bool m_needVertexUpdate;
bool m_isPicked; //!< Indicates whether the box is currently picked or not.
WPosition m_pickedPosition; //!< Caches the old picked position to a allow for cmoparison
WVector3d m_pickNormal; //!< Store the normal that occured when the pick action was started.
......@@ -135,6 +164,13 @@ private:
traverse( node, nv );
}
};
/**
* Called when the specified property has changed. Used to update the ROI when modifying box properties.
*
* \param property the property
*/
void boxPropertiesChanged( boost::shared_ptr< WPropertyBase > property );
};
#endif // WROIBOX_H
......@@ -2,7 +2,7 @@
//
// Project: OpenWalnut ( http://www.openwalnut.org )
//
// Copyright 2009 OpenWalnut Community, BSV-Leipzig and CNCF-CBS
// Copyright 2009 OpenWalnut Community, BSV@Uni-Leipzig and CNCF@MPI-CBS
// For more information see http://www.openwalnut.org/copying
//
// This file is part of OpenWalnut.
......@@ -22,49 +22,24 @@
//
//---------------------------------------------------------------------------
#ifndef WGELIGHTING_FRAGMENT_GLSL
#define WGELIGHTING_FRAGMENT_GLSL
#version 120
varying vec3 normal;
varying vec4 vertex;
varying vec3 halfvec;
#include "WGEShadingTools.glsl"
const vec4 AMBIENT_BLACK = vec4( 0.0, 0.0, 0.0, 1.0 );
const vec4 DEFAULT_BLACK = vec4( 0.0, 0.0, 0.0, 0.0 );
// The surface normal
varying vec3 v_normal;
void directionalLight( in int i, in vec3 normal, in float shininess,
inout vec4 ambient, inout vec4 diffuse, inout vec4 specular )
void main()
{
float nDotVP;
float nDotHV;
float pf;
vec3 L = normalize( gl_LightSource[i].position.xyz - vertex.xyz );
vec3 H = normalize( L + halfvec.xyz );
nDotVP = max( 0.0, dot( normal, normalize( ( gl_LightSource[i].position.xyz ) ) ) );
nDotHV = max( 0.0, dot( normal, H ) );
vec4 col = gl_Color;
if( nDotVP == 0.0 )
{
pf = 0.0;
}
else
{
pf = pow( nDotHV, gl_FrontMaterial.shininess );
}
// do light
float light = blinnPhongIlluminationIntensity( normalize( viewAlign( v_normal ) ) );
ambient += gl_LightSource[i].ambient;
diffuse += gl_LightSource[i].diffuse * nDotVP;
specular += gl_LightSource[i].specular * pf;
}
// opacity of the surface
col.rgb *= light;
void calculateLighting( in vec3 N, in float shininess, inout vec4 ambient, inout vec4 diffuse, inout vec4 specular )
{
directionalLight( 0, N, shininess, ambient, diffuse, specular );
// finally set the color
gl_FragColor = col;
}
#endif // WGELIGHTING_FRAGMENT_GLSL
......@@ -2,7 +2,7 @@
//
// Project: OpenWalnut ( http://www.openwalnut.org )
//
// Copyright 2009 OpenWalnut Community, BSV-Leipzig and CNCF-CBS
// Copyright 2009 OpenWalnut Community, BSV@Uni-Leipzig and CNCF@MPI-CBS
// For more information see http://www.openwalnut.org/copying
//
// This file is part of OpenWalnut.
......@@ -22,33 +22,19 @@
//
//---------------------------------------------------------------------------
#ifndef WGELIGHTING_VERTEX_GLSL
#define WGELIGHTING_VERTEX_GLSL
#version 120
varying vec3 normal;
varying vec4 vertex;
varying vec3 halfvec;
#include "WGETransformationTools.glsl"
const vec4 AMBIENT_BLACK = vec4( 0.0, 0.0, 0.0, 1.0 );
const vec4 DEFAULT_BLACK = vec4( 0.0, 0.0, 0.0, 0.0 );
// The surface normal
varying vec3 v_normal;
/**
* Computes normal and makes transformation to eye space.
*/
void prepareLight()
void main()
{
// Calculate the normal
normal = normalize( gl_NormalMatrix * gl_Normal ).xyz;
// Transform the vertex position to eye space
vertex = vec4( gl_ModelViewMatrix * gl_Vertex );
// prepare light
v_normal = gl_NormalMatrix * gl_Normal;
vec3 L = normalize( gl_LightSource[0].position.xyz - vertex.xyz );
halfvec = vec3( L + vec3( 0.0, 0.0, 1.0 ) );
gl_FrontColor = gl_Color;
gl_Position = ftransform();
}
#endif // WGELIGHTING_VERTEX_GLSL
......@@ -56,6 +56,11 @@ void WRMBranch::properties()
m_changeRoiSignal = boost::shared_ptr< boost::function< void() > >( new boost::function< void() >( boost::bind( &WRMBranch::setDirty, this ) ) );
}
WPropertyGroup::SPtr WRMBranch::getProperties() const
{
return m_properties;
}
void WRMBranch::propertyChanged()
{
setDirty();
......@@ -118,6 +123,16 @@ void WRMBranch::getRois( std::vector< osg::ref_ptr< WROI > >& roiVec ) // NOLINT
}
}
WROIManager::ROIs WRMBranch::getRois() const
{
WROIManager::ROIs ret;
for( std::list< osg::ref_ptr< WROI > >::const_iterator iter = m_rois.begin(); iter != m_rois.end(); ++iter )
{
ret.push_back( ( *iter ) );
}
return ret;
}
void WRMBranch::removeAllRois()
{
for( std::list< osg::ref_ptr< WROI > >::iterator iter = m_rois.begin(); iter != m_rois.end(); ++iter )
......
......@@ -35,8 +35,6 @@
#include "../graphicsEngine/WROI.h"
class WROIManager;
/**
......@@ -45,6 +43,16 @@ class WROIManager;
class WRMBranch : public boost::enable_shared_from_this< WRMBranch >
{
public:
/**
* Convenience type for a shared pointer of this type
*/
typedef boost::shared_ptr< WRMBranch > SPtr;
/**
* Convenience type for a const shared pointer of this type
*/
typedef boost::shared_ptr< const WRMBranch > ConstSPtr;
/**
* construtor
* \param roiManager
......@@ -77,6 +85,13 @@ public:
*/
WPropColor colorProperty();
/**
* Get the properties of this branch as group.
*
* \return branch property group
*/
WPropertyGroup::SPtr getProperties() const;
/**
* adds a roi to the branch
*
......@@ -157,6 +172,13 @@ public:
*/
void getRois( std::vector< osg::ref_ptr< WROI > >& roiVec ); //NOLINT
/**
* Create a list of ROIs of the current point in time.
*
* \return the ROIs
*/
std::vector< osg::ref_ptr< WROI > > getRois() const;
/**
* Add a specified notifier to the list of default notifiers which get connected to each branch
*
......
......@@ -227,13 +227,27 @@ osg::ref_ptr< WROI > WROIManager::getSelectedRoi()
return m_selectedRoi;
}
std::vector< osg::ref_ptr< WROI > > WROIManager::getRois()
WROIManager::ROIs WROIManager::getRois() const
{
std::vector< osg::ref_ptr< WROI > > returnVec;
ROIs returnVec;
for( std::list< boost::shared_ptr< WRMBranch > >::iterator iter = m_branches.begin(); iter != m_branches.end(); ++iter )
for( std::list< boost::shared_ptr< WRMBranch > >::const_iterator iter = m_branches.begin(); iter != m_branches.end(); ++iter )
{
( *iter )->getRois( returnVec );
}
return returnVec;
}
WROIManager::Branches WROIManager::getBranches() const
{
// copy to this vec
Branches returnVec;
// copy
for( std::list< boost::shared_ptr< WRMBranch > >::const_iterator iter = m_branches.begin(); iter != m_branches.end(); ++iter )
{
returnVec.push_back( *iter );
}
return returnVec;
}
......@@ -163,11 +163,28 @@ public:
*/
boost::shared_ptr< WProperties > getProperties();
/**
* ROI list
*/
typedef std::vector< osg::ref_ptr< WROI > > ROIs;
/**
* getter
* \return all existing rois
*/
std::vector< osg::ref_ptr< WROI > > getRois();
ROIs getRois() const;
/**
* Branches list
*/
typedef std::vector< boost::shared_ptr< WRMBranch > > Branches;
/**
* Get a copy of the current branch list. Please note that after getting the list, it might already have been changed by another thread.
*
* \return the list of current branches
*/
Branches getBranches() const;
protected:
private:
......
......@@ -25,6 +25,10 @@
#include <string>
#include "../common/WLogger.h"
#include "../graphicsEngine/WROI.h"
#include "../graphicsEngine/WROIBox.h"
#include "WROIManager.h"
#include "WKernel.h"
#include "WRoiProjectFileIO.h"
......@@ -57,8 +61,38 @@ void WRoiProjectFileIO::save( std::ostream& output ) // NOLINT
"// ROI Structure" << std::endl <<
"//////////////////////////////////////////////////////////////////////////////////////////////////////////////////" << std::endl <<
std::endl;
output << "// Sorry. Not Yet Implemented." << std::endl;
wlog::info( "ROI Project File" ) << "Not yet implemented. Sorry.";
// write all branches
WROIManager::Branches branches =WKernel::getRunningKernel()->getRoiManager()->getBranches();
unsigned int branchIndex = 0;
for( WROIManager::Branches::const_iterator branchIter = branches.begin(); branchIter != branches.end(); ++branchIter )
{
// get the branch
WRMBranch::SPtr branch = *branchIter;
// write this branch's properties
output << "SELECTOR_BRANCH:" << branchIndex << std::endl;
printProperties( output, branch->getProperties(), "", "", branchIndex, "SELECTOR_BRANCH" );
output << std::endl;
// handle this branch's ROIs
WROIManager::ROIs rois = branch->getRois();
unsigned int roiIndex = 0;
for( WROIManager::ROIs::const_iterator roiIter = rois.begin(); roiIter != rois.end(); ++roiIter )
{
// differentiate the type of roi, currently we will support only WROiBox
WROIBox* roiBox = dynamic_cast< WROIBox* >( ( *roiIter ).get() );
output << "SELECTOR_ROIBOX:" << roiIndex << ":SELECTOR_BRANCH" << branchIndex << std::endl;
printProperties( output, roiBox->getProperties(), "", "", roiIndex, "SELECTOR_ROIBOX" );
output << std::endl;
// done
roiIndex++;
}
// done
branchIndex++;
}
}
<
......@@ -29,8 +29,6 @@
#include "../common/WProjectFileIO.h"