Commit 734a59a7 authored by Pierre Kraemer's avatar Pierre Kraemer

SCHNApps: debug surface deformation

parent 9a08b7b1
......@@ -7,5 +7,5 @@ ADD_SUBDIRECTORY(render)
ADD_SUBDIRECTORY(renderVector)
ADD_SUBDIRECTORY(renderExplod)
ADD_SUBDIRECTORY(subdivideSurface)
#ADD_SUBDIRECTORY(surfaceDeformation)
ADD_SUBDIRECTORY(surfaceDeformation)
#ADD_SUBDIRECTORY(renderTopoSurface)
......@@ -27,7 +27,7 @@
</widget>
</item>
<item>
<widget class="QComboBox" name="combo_positionVBO">
<widget class="QComboBox" name="combo_positionAttribute">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Fixed">
<horstretch>0</horstretch>
......
......@@ -2,27 +2,34 @@
#define _SURFACEDEFORMATION_PLUGIN_H_
#include "plugin.h"
#include "mapHandler.h"
#include "ui_surfaceDeformation.h"
#include "Utils/drawer.h"
using namespace CGoGN;
using namespace SCHNApps;
enum SelectionMode
{
LOCKED,
HANDLE
};
struct PerMapParameterSet
{
PerMapParameterSet() {}
PerMapParameterSet(MapHandlerGen* mh);
~PerMapParameterSet();
VertexAttribute<PFP2::VEC3> positionAttribute;
CellMarker<VERTEX> lockingMarker;
bool setLockedVertices;
bool selecting;
PFP2::VEC3 selectionCenter;
PFP2::REAL selectionRadius;
bool dragging;
PFP2::REAL dragZ;
qglviewer::Vec dragPrevious;
CellMarker<VERTEX>* lockingMarker;
CellMarker<VERTEX>* handleMarker;
SelectionMode verticesSelectionMode;
std::vector<unsigned int> locked_vertices;
std::vector<unsigned int> handle_vertices;
};
......@@ -32,12 +39,12 @@ struct ParameterSet
ParameterSet() : selectedMap(NULL)
{}
PerMapParameterSet& getCurrentMapParameterSet()
PerMapParameterSet* getCurrentMapParameterSet()
{
return perMap[selectedMap->getName()];
}
QHash<QString, PerMapParameterSet> perMap;
QHash<QString, PerMapParameterSet*> perMap;
MapHandlerGen* selectedMap;
};
......@@ -65,7 +72,10 @@ class SurfaceDeformationPlugin : public Plugin
Q_INTERFACES(CGoGN::SCHNApps::Plugin)
public:
SurfaceDeformationPlugin() : b_refreshingUI(false)
SurfaceDeformationPlugin() :
b_refreshingUI(false),
selecting(false),
dragging(false)
{
setProvidesRendering(true);
}
......@@ -74,7 +84,7 @@ public:
{}
virtual bool enable();
virtual void disable() {}
virtual void disable();
virtual void redraw(View *view);
......@@ -95,17 +105,31 @@ public slots:
void mapLinked(MapHandlerGen* m);
void mapUnlinked(MapHandlerGen* m);
void attributeAdded();
void changeSelectedMap(View* view, MapHandlerGen* map);
void changePositionAttribute(View* view, MapHandlerGen* map, VertexAttribute<PFP2::VEC3> attribute);
void changeVerticesSelectionMode(View* view, MapHandlerGen* map, SelectionMode m);
void cb_selectedMapChanged();
void cb_positionAttributeChanged(int index);
void cb_selectLockedVertices(bool b);
void cb_selectHandleVertices(bool b);
private:
RenderVectorDockTab* m_dockTab;
SurfaceDeformationDockTab* m_dockTab;
QHash<View*, ParameterSet*> h_viewParams;
Utils::Drawer* m_drawer;
bool b_refreshingUI;
bool selecting;
PFP2::VEC3 selectionCenter;
PFP2::REAL selectionRadius;
bool dragging;
PFP2::REAL dragZ;
qglviewer::Vec dragPrevious;
};
#endif
......@@ -3,14 +3,18 @@
#include "Algo/Selection/raySelector.h"
#include "Algo/Selection/collector.h"
#include <QKeyEvent>
#include <QMouseEvent>
PerMapParameterSet::PerMapParameterSet(MapHandlerGen* mh) :
setLockedVertices(true),
selecting(false),
selectionRadius(0.1f),
dragging(false)
verticesSelectionMode(LOCKED)
{
GenericMap* map = mh->getGenericMap();
lockingMarker = new CellMarker<VERTEX>(*map);
handleMarker = new CellMarker<VERTEX>(*map);
AttributeContainer& cont = map->getAttributeContainer<VERTEX>();
std::vector<std::string> names;
......@@ -23,7 +27,7 @@ PerMapParameterSet::PerMapParameterSet(MapHandlerGen* mh) :
if(types[i] == vec3TypeName)
{
if(names[i] == "position") // try to select a position attribute named "position"
positionAttribute = mh->getAttribute<PFP2::VEC3>(names[i]);
positionAttribute = mh->getAttribute<PFP2::VEC3, VERTEX>(QString::fromStdString(names[i]));
}
}
......@@ -33,13 +37,19 @@ PerMapParameterSet::PerMapParameterSet(MapHandlerGen* mh) :
{
if(types[i] == vec3TypeName)
{
positionAttribute = mh->getAttribute<PFP2::VEC3>(names[i]);
positionAttribute = mh->getAttribute<PFP2::VEC3, VERTEX>(QString::fromStdString(names[i]));
break;
}
}
}
}
PerMapParameterSet::~PerMapParameterSet()
{
delete lockingMarker;
delete handleMarker;
}
bool SurfaceDeformationPlugin::enable()
{
......@@ -48,22 +58,85 @@ bool SurfaceDeformationPlugin::enable()
connect(m_dockTab->mapList, SIGNAL(itemSelectionChanged()), this, SLOT(cb_selectedMapChanged()));
connect(m_dockTab->combo_positionAttribute, SIGNAL(currentIndexChanged(int)), this, SLOT(cb_positionAttributeChanged(int)));
connect(m_dockTab->radio_locked, SIGNAL(toggled(bool)), this, SLOT(cb_selectLockedVertices(bool)));
connect(m_dockTab->radio_handle, SIGNAL(toggled(bool)), this, SLOT(cb_selectHandleVertices(bool)));
connect(m_window, SIGNAL(viewAndPluginLinked(View*, Plugin*)), this, SLOT(viewLinked(View*, Plugin*)));
connect(m_window, SIGNAL(viewAndPluginUnlinked(View*, Plugin*)), this, SLOT(viewUnlinked(View*, Plugin*)));
connect(m_window, SIGNAL(currentViewChanged(View*)), this, SLOT(currentViewChanged(View*)));
Utils::ShaderColorPerVertex* s = new Utils::ShaderColorPerVertex();
registerShader(s);
m_drawer = new Utils::Drawer();
registerShader(m_drawer->getShader());
return true;
}
void SurfaceDeformationPlugin::disable()
{
delete m_drawer;
}
void SurfaceDeformationPlugin::redraw(View* view)
{
if(selecting)
{
glDisable(GL_LIGHTING) ;
m_drawer->newList(GL_COMPILE_AND_EXECUTE) ;
m_drawer->lineWidth(2.0f) ;
m_drawer->begin(GL_LINES) ;
m_drawer->color3f(0.0f, 0.0f, 1.0f) ;
m_drawer->vertex(selectionCenter) ;
m_drawer->vertex(selectionCenter + selectionRadius * PFP2::VEC3(1,0,0)) ;
m_drawer->vertex(selectionCenter) ;
m_drawer->vertex(selectionCenter + selectionRadius * PFP2::VEC3(-1,0,0)) ;
m_drawer->vertex(selectionCenter) ;
m_drawer->vertex(selectionCenter + selectionRadius * PFP2::VEC3(0,1,0)) ;
m_drawer->vertex(selectionCenter) ;
m_drawer->vertex(selectionCenter + selectionRadius * PFP2::VEC3(0,-1,0)) ;
m_drawer->vertex(selectionCenter) ;
m_drawer->vertex(selectionCenter + selectionRadius * PFP2::VEC3(0,0,1)) ;
m_drawer->vertex(selectionCenter) ;
m_drawer->vertex(selectionCenter + selectionRadius * PFP2::VEC3(0,0,-1)) ;
m_drawer->end() ;
m_drawer->endList() ;
}
ParameterSet* params = h_viewParams[view];
MapHandlerGen* mh = params->selectedMap;
if(mh)
{
PerMapParameterSet* perMap = params->perMap[mh->getName()];
if(!perMap->locked_vertices.empty() || !perMap->handle_vertices.empty())
{
glDisable(GL_LIGHTING) ;
m_drawer->newList(GL_COMPILE_AND_EXECUTE) ;
m_drawer->pointSize(4.0f) ;
m_drawer->begin(GL_POINTS) ;
m_drawer->color3f(1.0f, 0.0f, 0.0f) ;
for(unsigned int i = 0; i < perMap->locked_vertices.size(); ++i)
{
if (!perMap->handleMarker->isMarked(perMap->locked_vertices[i]))
m_drawer->vertex(perMap->positionAttribute[perMap->locked_vertices[i]]) ;
}
m_drawer->color3f(0.0f, 0.0f, 1.0f) ;
for(unsigned int i = 0; i < perMap->handle_vertices.size(); ++i)
m_drawer->vertex(perMap->positionAttribute[perMap->handle_vertices[i]]) ;
m_drawer->end() ;
m_drawer->endList() ;
}
}
}
void SurfaceDeformationPlugin::keyPress(View* view, QKeyEvent* event)
{
if(event->key() == Qt::Key_Shift)
{
view->setMouseTracking(true);
ParameterSet* params = h_viewParams[view];
PerMapParameterSet& perMap = params->getCurrentMapParameterSet();
perMap.selecting = true;
selecting = true;
view->updateGL();
}
}
......@@ -73,127 +146,122 @@ void SurfaceDeformationPlugin::keyRelease(View* view, QKeyEvent* event)
if(event->key() == Qt::Key_Shift)
{
view->setMouseTracking(false);
ParameterSet* params = h_viewParams[view];
PerMapParameterSet& perMap = params->getCurrentMapParameterSet();
perMap.selecting = false;
selecting = false;
view->updateGL();
}
}
void SurfaceDeformationPlugin::mousePress(View* view, QMouseEvent* event)
{
if(event->button() == Qt::RightButton && event->modifiers() & Qt::ShiftModifier)
if(event->button() == Qt::LeftButton && selecting)
{
view->setMouseTracking(false) ;
ParameterSet* params = h_viewParams[view];
PerMapParameterSet& perMap = params->getCurrentMapParameterSet();
perMap.selecting = false ;
perMap.dragging = true ;
perMap.dragZ = 0;
for(unsigned int i = 0; i < perMap.handle_vertices.size(); ++i)
{
PFP::VEC3& p = perMap.positionAttribute[handle_vertices[i]] ;
qglviewer::Vec q = view->projectedCoordinatesOf(qglviewer::Vec(p[0],p[1],p[2]));
dragZ += q.z ;
}
dragZ /= handle_vertices.size() ;
qglviewer::Vec p(event->x(), event->y(), dragZ);
perMap.dragPrevious = view->unprojectedCoordinatesOf(p);
}
if(button == Qt::LeftButton && event->modifiers() & Qt::ShiftModifier)
{
ParameterSet* params = h_viewParams[view];
PerMapParameterSet& perMap = params->getCurrentMapParameterSet();
PerMapParameterSet* perMap = params->getCurrentMapParameterSet();
QPoint pixel(event->x(), event->y());
qglviewer::Vec orig;
qglviewer::Vec dir;
view->convertClickToLine(pixel, orig, dir);
view->camera()->convertClickToLine(pixel, orig, dir);
PFP::VEC3 rayA(orig.x, orig.y, orig.z);
PFP::VEC3 AB(dir.x, dir.y, dir.z);
PFP2::VEC3 rayA(orig.x, orig.y, orig.z);
PFP2::VEC3 AB(dir.x, dir.y, dir.z);
Dart d ;
PFP2::MAP map = static_cast<MapHandler<PFP2>*>(params->selectedMap)->getMap();
Algo::Selection::vertexRaySelection<PFP>(*map, position, rayA, AB, d) ;
PFP2::MAP* map = static_cast<MapHandler<PFP2>*>(params->selectedMap)->getMap();
Algo::Selection::vertexRaySelection<PFP2>(*map, perMap->positionAttribute, rayA, AB, d) ;
if(d != NIL)
{
Algo::Surface::Selection::Collector_WithinSphere<PFP> neigh(*map, perMap.positionAttribute, perMap.selectionRadius) ;
Algo::Surface::Selection::Collector_WithinSphere<PFP2> neigh(*map, perMap->positionAttribute, selectionRadius) ;
neigh.collectAll(d) ;
const std::vector<Dart>& insideV = neigh.getInsideVertices() ;
if(perMap.setLockedVertices)
if(perMap->verticesSelectionMode == LOCKED)
{
for(unsigned int i = 0; i < insideV.size(); ++i)
{
unsigned int v = map->getEmbedding<VERTEX>(insideV[i]) ;
if (!lockingMarker.isMarked(v))
if (!perMap->lockingMarker->isMarked(v))
{
locked_vertices.push_back(v) ;
lockingMarker.mark(v);
perMap->locked_vertices.push_back(v) ;
perMap->lockingMarker->mark(v);
}
}
LinearSolving::resetSolver(solver, false) ;
}
else
{
for(unsigned int i = 0; i < insideV.size(); ++i)
{
unsigned int v = myMap.getEmbedding<VERTEX>(insideV[i]) ;
if(!handleMarker.isMarked(v))
unsigned int v = map->getEmbedding<VERTEX>(insideV[i]) ;
if(!perMap->handleMarker->isMarked(v))
{
handle_vertices.push_back(v) ;
handleMarker.mark(v);
perMap->handle_vertices.push_back(v) ;
perMap->handleMarker->mark(v);
}
if(!lockingMarker.isMarked(v))
if(!perMap->lockingMarker->isMarked(v))
{
locked_vertices.push_back(v) ;
lockingMarker.mark(v) ;
perMap->locked_vertices.push_back(v) ;
perMap->lockingMarker->mark(v) ;
}
}
LinearSolving::resetSolver(solver, false) ;
}
view->updateGL() ;
}
}
else if(event->button() == Qt::RightButton && event->modifiers() & Qt::ShiftModifier)
{
view->setMouseTracking(false) ;
ParameterSet* params = h_viewParams[view];
PerMapParameterSet* perMap = params->getCurrentMapParameterSet();
selecting = false ;
dragging = true ;
dragZ = 0;
for(unsigned int i = 0; i < perMap->handle_vertices.size(); ++i)
{
const PFP2::VEC3& p = perMap->positionAttribute[perMap->handle_vertices[i]] ;
qglviewer::Vec q = view->camera()->projectedCoordinatesOf(qglviewer::Vec(p[0],p[1],p[2]));
dragZ += q.z ;
}
dragZ /= perMap->handle_vertices.size() ;
qglviewer::Vec p(event->x(), event->y(), dragZ);
dragPrevious = view->camera()->unprojectedCoordinatesOf(p);
}
}
void SurfaceDeformationPlugin::mouseRelease(View* view, QMouseEvent* event)
{
if(event->button() == Qt::RightButton)
{
ParameterSet* params = h_viewParams[view];
PerMapParameterSet& perMap = params->getCurrentMapParameterSet();
perMap.dragging = false ;
dragging = false ;
}
}
void SurfaceDeformationPlugin::mouseMove(View* view, QMouseEvent* event)
{
ParameterSet* params = h_viewParams[view];
PerMapParameterSet& perMap = params->getCurrentMapParameterSet();
if(perMap.dragging)
PerMapParameterSet* perMap = params->getCurrentMapParameterSet();
if(dragging)
{
qglviewer::Vec p(event->x(), event->y(), perMap.dragZ);
qglviewer::Vec q = view->unprojectedCoordinatesOf(p);
qglviewer::Vec p(event->x(), event->y(), dragZ);
qglviewer::Vec q = view->camera()->unprojectedCoordinatesOf(p);
qglviewer::Vec vec = q - perMap.dragPrevious;
PFP::VEC3 t(vec.x, vec.y, vec.z);
for(unsigned int i = 0; i < handle_vertices.size(); ++i)
perMap.positionAttribute[handle_vertices[i]] += t ;
qglviewer::Vec vec = q - dragPrevious;
PFP2::VEC3 t(vec.x, vec.y, vec.z);
for(unsigned int i = 0; i < perMap->handle_vertices.size(); ++i)
perMap->positionAttribute[perMap->handle_vertices[i]] += t ;
perMap.dragPrevious = q ;
dragPrevious = q ;
// matchDiffCoord() ;
// for(unsigned int i = 0; i < 2; ++i)
// asRigidAsPossible();
m_positionVBO->updateData(position);
params->selectedMap->updateVBO(perMap->positionAttribute);
view->updateGL();
}
......@@ -202,22 +270,34 @@ void SurfaceDeformationPlugin::mouseMove(View* view, QMouseEvent* event)
QPoint pixel(event->x(), event->y());
qglviewer::Vec orig;
qglviewer::Vec dir;
view->convertClickToLine(pixel, orig, dir);
view->camera()->convertClickToLine(pixel, orig, dir);
PFP::VEC3 rayA(orig.x, orig.y, orig.z);
PFP::VEC3 AB(dir.x, dir.y, dir.z);
PFP2::VEC3 rayA(orig.x, orig.y, orig.z);
PFP2::VEC3 AB(dir.x, dir.y, dir.z);
Dart d ;
PFP2::MAP map = static_cast<MapHandler<PFP2>*>(params->selectedMap)->getMap();
Algo::Selection::vertexRaySelection<PFP2>(*map, position, rayA, AB, d) ;
PFP2::MAP* map = static_cast<MapHandler<PFP2>*>(params->selectedMap)->getMap();
Algo::Selection::vertexRaySelection<PFP2>(*map, perMap->positionAttribute, rayA, AB, d) ;
if(d != NIL)
{
perMap.selectionCenter = perMap.positionAttribute[d] ;
selectionCenter = perMap->positionAttribute[d] ;
view->updateGL() ;
}
}
}
void SurfaceDeformationPlugin::wheelEvent(View* view, QWheelEvent* event)
{
if(selecting)
{
if(event->delta() > 0)
selectionRadius *= 0.9f ;
else
selectionRadius *= 1.1f ;
view->updateGL() ;
}
}
void SurfaceDeformationPlugin::viewLinked(View* view, Plugin* plugin)
{
if(plugin == this)
......@@ -227,7 +307,7 @@ void SurfaceDeformationPlugin::viewLinked(View* view, Plugin* plugin)
const QList<MapHandlerGen*>& maps = view->getLinkedMaps();
foreach(MapHandlerGen* map, maps)
{
PerMapParameterSet p(map);
PerMapParameterSet* p = new PerMapParameterSet(map);
params->perMap.insert(map->getName(), p);
}
if (!maps.empty())
......@@ -245,6 +325,13 @@ void SurfaceDeformationPlugin::viewUnlinked(View* view, Plugin* plugin)
{
if(plugin == this)
{
ParameterSet* params = h_viewParams[view];
QHash<QString, PerMapParameterSet*>::const_iterator i = params->perMap.constBegin();
while (i != params->perMap.constEnd())
{
delete i.value();
++i;
}
h_viewParams.remove(view);
disconnect(view, SIGNAL(mapLinked(MapHandlerGen*)), this, SLOT(mapLinked(MapHandlerGen*)));
......@@ -264,7 +351,7 @@ void SurfaceDeformationPlugin::mapLinked(MapHandlerGen* m)
assert(isLinkedToView(view));
ParameterSet* params = h_viewParams[view];
PerMapParameterSet p(m);
PerMapParameterSet* p = new PerMapParameterSet(m);
params->perMap.insert(m->getName(), p);
if(params->selectedMap == NULL || params->perMap.count() == 1)
changeSelectedMap(view, m);
......@@ -278,6 +365,7 @@ void SurfaceDeformationPlugin::mapUnlinked(MapHandlerGen* m)
assert(isLinkedToView(view));
ParameterSet* params = h_viewParams[view];
delete params->perMap[m->getName()];
params->perMap.remove(m->getName());
if(params->selectedMap == m)
......@@ -291,6 +379,12 @@ void SurfaceDeformationPlugin::mapUnlinked(MapHandlerGen* m)
m_dockTab->refreshUI(params);
}
void SurfaceDeformationPlugin::attributeAdded()
{
ParameterSet* params = h_viewParams[m_window->getCurrentView()];
m_dockTab->refreshUI(params);
}
void SurfaceDeformationPlugin::changeSelectedMap(View* view, MapHandlerGen* map)
{
ParameterSet* params = h_viewParams[view];
......@@ -305,6 +399,8 @@ void SurfaceDeformationPlugin::changeSelectedMap(View* view, MapHandlerGen* map)
if(map)
connect(map, SIGNAL(attributeAdded()), this, SLOT(attributeAdded()));
selectionRadius = map->getBBdiagSize() / 50.0;
m_dockTab->refreshUI(params);
view->updateGL();
}
......@@ -313,12 +409,24 @@ void SurfaceDeformationPlugin::changeSelectedMap(View* view, MapHandlerGen* map)
void SurfaceDeformationPlugin::changePositionAttribute(View* view, MapHandlerGen* map, VertexAttribute<PFP2::VEC3> attribute)
{
ParameterSet* params = h_viewParams[view];
params->perMap[map->getName()].positionAttribute = attribute;
params->perMap[map->getName()]->positionAttribute = attribute;
if(view->isCurrentView())
{
m_dockTab->refreshUI(params);
view->updateGL();
// view->updateGL();
}
}
void SurfaceDeformationPlugin::changeVerticesSelectionMode(View* view, MapHandlerGen* map, SelectionMode m)
{
ParameterSet* params = h_viewParams[view];
params->perMap[map->getName()]->verticesSelectionMode = m;
if(view->isCurrentView())
{
m_dockTab->refreshUI(params);
// view->updateGL();
}
}
......@@ -338,10 +446,105 @@ void SurfaceDeformationPlugin::cb_positionAttributeChanged(int index)
{
View* view = m_window->getCurrentView();
MapHandlerGen* map = h_viewParams[view]->selectedMap;
changePositionAttribute(view, map, map->getAttribute<PFP2::VEC3>(m_dockTab->combo_positionVBO->currentText()));
changePositionAttribute(view, map, map->getAttribute<PFP2::VEC3, VERTEX>(m_dockTab->combo_positionAttribute->currentText()));
}
}
void SurfaceDeformationPlugin::cb_selectLockedVertices(bool b)
{
if(!b_refreshingUI)
{
View* view = m_window->getCurrentView();
MapHandlerGen* map = h_viewParams[view]->selectedMap;
changeVerticesSelectionMode(view, map, LOCKED);
}
}
void SurfaceDeformationPlugin::cb_selectHandleVertices(bool b)
{
if(!b_refreshingUI)
{
View* view = m_window->getCurrentView();
MapHandlerGen* map = h_viewParams[view]->selectedMap;
changeVerticesSelectionMode(view, map, HANDLE);
}
}
void SurfaceDeformationDockTab::refreshUI(ParameterSet* params)
{
plugin->setRefreshingUI(true);
mapList->clear();
combo_positionAttribute->clear();
MapHandlerGen* mh = params->selectedMap;
QHash<QString, PerMapParameterSet*>::const_iterator i = params->perMap.constBegin();
while (i != params->perMap.constEnd())
{
mapList->addItem(i.key());
if(mh != NULL && i.key() == mh->getName())
{
QList<QListWidgetItem*> item = mapList->findItems(mh->getName(), Qt::MatchExactly);
item[0]->setSelected(true);
PerMapParameterSet* p = params->perMap[mh->getName()];
GenericMap* map = mh->getGenericMap();
AttributeContainer& cont = map->getAttributeContainer<VERTEX>();
std::vector<std::string> names;
std::vector<std::string> types;
cont.getAttributesNames(names);
cont.getAttributesTypes(types);
std::string vec3TypeName = nameOfType(PFP2::VEC3());
unsigned int j = 0;
for(unsigned int i = 0; i < names.size(); ++i)