Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
C
CGoGN
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
1
Issues
1
List
Boards
Labels
Service Desk
Milestones
Merge Requests
0
Merge Requests
0
Operations
Operations
Incidents
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
CGoGN
CGoGN
Commits
49e7e333
Commit
49e7e333
authored
Mar 02, 2011
by
Kenneth Vanhoey
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
passed to new container format for plyptm : good for glsl (only vec3)
parent
195e3fc5
Changes
9
Hide whitespace changes
Inline
Side-by-side
Showing
9 changed files
with
838 additions
and
157 deletions
+838
-157
include/Algo/Decimation/approximator.h
include/Algo/Decimation/approximator.h
+1
-0
include/Algo/Decimation/decimation.hpp
include/Algo/Decimation/decimation.hpp
+8
-2
include/Algo/Decimation/lightfieldApproximator.h
include/Algo/Decimation/lightfieldApproximator.h
+49
-0
include/Algo/Decimation/lightfieldApproximator.hpp
include/Algo/Decimation/lightfieldApproximator.hpp
+94
-1
include/Algo/Decimation/selector.h
include/Algo/Decimation/selector.h
+117
-1
include/Algo/Decimation/selector.hpp
include/Algo/Decimation/selector.hpp
+537
-4
include/Algo/Export/export.h
include/Algo/Export/export.h
+4
-13
include/Algo/Export/export.hpp
include/Algo/Export/export.hpp
+8
-130
include/Algo/Import/import2tablesSurface.hpp
include/Algo/Import/import2tablesSurface.hpp
+20
-6
No files found.
include/Algo/Decimation/approximator.h
View file @
49e7e333
...
...
@@ -44,6 +44,7 @@ enum ApproximatorType
A_CornerCutting
,
A_TangentPredict1
,
A_TangentPredict2
,
A_LightfieldHalf
,
A_LightfieldFull
}
;
...
...
include/Algo/Decimation/decimation.hpp
View file @
49e7e333
...
...
@@ -71,11 +71,11 @@ void decimate(
}
case
A_LightfieldHalf
:
{
approximators
.
push_back
(
new
Approximator_
QEM
<
PFP
>
(
map
,
position
))
;
approximators
.
push_back
(
new
Approximator_
HalfCollapse
<
PFP
>
(
map
,
position
))
;
AttributeHandler
<
Geom
::
Matrix
<
3
,
3
,
typename
PFP
::
REAL
>
>
frame
=
map
.
template
getAttribute
<
Geom
::
Matrix
<
3
,
3
,
typename
PFP
::
REAL
>
>
(
VERTEX_ORBIT
,
"frame"
)
;
AttributeHandler
<
Geom
::
Matrix
<
3
,
6
,
typename
PFP
::
REAL
>
>
RGBfunctions
=
map
.
template
getAttribute
<
Geom
::
Matrix
<
3
,
6
,
typename
PFP
::
REAL
>
>
(
VERTEX_ORBIT
,
"colorPTM"
)
;
approximators
.
push_back
(
new
Approximator_FrameHalf
<
PFP
>
(
map
,
frame
))
;
approximators
.
push_back
(
new
Approximator_RGBfunctions
<
PFP
>
(
map
,
RGBfunctions
))
;
approximators
.
push_back
(
new
Approximator_RGBfunctions
Half
<
PFP
>
(
map
,
RGBfunctions
))
;
break
;
}
}
...
...
@@ -91,12 +91,18 @@ void decimate(
case
S_EdgeLength
:
selector
=
new
EdgeSelector_Length
<
PFP
>
(
map
,
position
,
approximators
)
;
break
;
case
S_QEMml
:
selector
=
new
EdgeSelector_QEMml
<
PFP
>
(
map
,
position
,
approximators
)
;
break
;
case
S_QEM
:
selector
=
new
EdgeSelector_QEM
<
PFP
>
(
map
,
position
,
approximators
)
;
break
;
case
S_Lightfield
:
selector
=
new
EdgeSelector_Lightfield
<
PFP
>
(
map
,
position
,
approximators
)
;
break
;
case
S_LightfieldHalf
:
selector
=
new
HalfEdgeSelector_Lightfield
<
PFP
>
(
map
,
position
,
approximators
)
;
break
;
case
S_Curvature
:
selector
=
new
EdgeSelector_Curvature
<
PFP
>
(
map
,
position
,
approximators
)
;
break
;
...
...
include/Algo/Decimation/lightfieldApproximator.h
View file @
49e7e333
...
...
@@ -36,6 +36,55 @@ namespace Algo
namespace
Decimation
{
template
<
typename
PFP
>
class
Approximator_FrameHalf
:
public
Approximator
<
PFP
,
typename
Geom
::
Matrix
<
3
,
3
,
typename
PFP
::
REAL
>
>
{
public:
typedef
typename
PFP
::
MAP
MAP
;
typedef
typename
PFP
::
VEC3
VEC3
;
typedef
typename
PFP
::
REAL
REAL
;
typedef
Geom
::
Matrix
<
3
,
3
,
REAL
>
MATRIX33
;
typedef
Geom
::
Matrix
<
3
,
6
,
REAL
>
MATRIX36
;
public:
Approximator_FrameHalf
(
MAP
&
m
,
AttributeHandler
<
MATRIX33
>&
frame
,
Predictor
<
PFP
,
MATRIX33
>*
pred
=
NULL
)
:
Approximator
<
PFP
,
MATRIX33
>
(
m
,
frame
,
EDGE_ORBIT
,
pred
)
{}
~
Approximator_FrameHalf
()
{}
ApproximatorType
getType
()
const
{
return
A_LightfieldHalf
;
}
bool
init
()
{
return
true
;
}
;
void
approximate
(
Dart
d
)
;
}
;
template
<
typename
PFP
>
class
Approximator_RGBfunctionsHalf
:
public
Approximator
<
PFP
,
typename
Geom
::
Matrix
<
3
,
6
,
typename
PFP
::
REAL
>
>
{
public:
typedef
typename
PFP
::
MAP
MAP
;
typedef
typename
PFP
::
VEC3
VEC3
;
typedef
typename
PFP
::
REAL
REAL
;
typedef
Geom
::
Matrix
<
3
,
3
,
REAL
>
MATRIX33
;
typedef
Geom
::
Matrix
<
3
,
6
,
REAL
>
MATRIX36
;
protected:
AttributeHandler
<
MATRIX33
>
m_frame
;
AttributeHandler
<
MATRIX33
>
m_approxFrame
;
AttributeHandler
<
QuadricRGBfunctions
<
REAL
>
>
m_quadricRGBfunctions
;
public:
Approximator_RGBfunctionsHalf
(
MAP
&
m
,
AttributeHandler
<
MATRIX36
>&
rgbfunctions
,
Predictor
<
PFP
,
MATRIX36
>*
pred
=
NULL
)
:
Approximator
<
PFP
,
MATRIX36
>
(
m
,
rgbfunctions
,
EDGE_ORBIT
,
pred
)
{
}
~
Approximator_RGBfunctionsHalf
()
{}
ApproximatorType
getType
()
const
{
return
A_LightfieldHalf
;
}
bool
init
()
;
void
approximate
(
Dart
d
)
;
}
;
template
<
typename
PFP
>
class
Approximator_Frame
:
public
Approximator
<
PFP
,
typename
Geom
::
Matrix
<
3
,
3
,
typename
PFP
::
REAL
>
>
{
...
...
include/Algo/Decimation/lightfieldApproximator.hpp
View file @
49e7e333
...
...
@@ -31,6 +31,96 @@ namespace Algo
namespace
Decimation
{
/************************************************************************************
* LIGHTFIELD QUADRIC METRIC : frame *
************************************************************************************/
template
<
typename
PFP
>
void
Approximator_FrameHalf
<
PFP
>::
approximate
(
Dart
d
)
{
this
->
m_approx
[
d
]
=
this
->
m_attrV
[
d
]
;
}
/************************************************************************************
* LIGHTFIELD QUADRIC METRIC : functions *
************************************************************************************/
template
<
typename
PFP
>
bool
Approximator_RGBfunctionsHalf
<
PFP
>::
init
()
{
// get actual frames and hypothetical approximated frames
m_frame
=
this
->
m_map
.
template
getAttribute
<
MATRIX33
>(
VERTEX_ORBIT
,
"frame"
)
;
m_approxFrame
=
this
->
m_map
.
template
getAttribute
<
MATRIX33
>(
EDGE_ORBIT
,
"approx_frame"
)
;
m_quadricRGBfunctions
=
this
->
m_map
.
template
getAttribute
<
QuadricRGBfunctions
<
REAL
>
>
(
EDGE_ORBIT
,
"quadricRGBfunctions"
)
;
MapBrowserLinkedAuto
<
typename
PFP
::
MAP
>
mb
(
this
->
m_map
)
;
this
->
m_map
.
foreach_orbit
(
EDGE_ORBIT
,
mb
)
;
// create quadric embedding for computing and set them to 0
for
(
Dart
d
=
mb
.
begin
()
;
d
!=
mb
.
end
()
;
mb
.
next
(
d
))
m_quadricRGBfunctions
[
d
].
zero
()
;
// Check on embeddings
if
(
!
m_frame
.
isValid
()
||
!
m_approxFrame
.
isValid
()
||
!
m_quadricRGBfunctions
.
isValid
())
{
std
::
cerr
<<
"Approximator_RGBfunctions::init() --> No approxPosition or no quadricRGBfunctions specified"
<<
std
::
endl
;
return
false
;
}
return
true
;
}
template
<
typename
PFP
>
void
Approximator_RGBfunctionsHalf
<
PFP
>::
approximate
(
Dart
d
)
{
MAP
&
m
=
this
->
m_map
;
Dart
dd
=
m
.
phi2
(
d
)
;
// get the two vertices
// Approximation
this
->
m_approx
[
d
]
=
this
->
m_attrV
[
d
]
;
// Compute quadrics for error evaluation
// get hypothetical local frames
VEC3
i
,
n
;
m_approxFrame
[
d
].
getSubVectorH
(
0
,
0
,
i
)
;
m_approxFrame
[
d
].
getSubVectorH
(
2
,
0
,
n
)
;
// Get previous local frames
VEC3
n1
,
n2
,
i1
,
i2
,
j1
,
j2
;
m_frame
[
d
].
getSubVectorH
(
0
,
0
,
i1
)
;
m_frame
[
dd
].
getSubVectorH
(
0
,
0
,
i2
)
;
m_frame
[
d
].
getSubVectorH
(
1
,
0
,
j1
)
;
m_frame
[
dd
].
getSubVectorH
(
1
,
0
,
j2
)
;
m_frame
[
d
].
getSubVectorH
(
2
,
0
,
n1
)
;
m_frame
[
dd
].
getSubVectorH
(
2
,
0
,
n2
)
;
// Compute j1' and j2'
VEC3
j1pr
=
n1
^
i
;
j1pr
.
normalize
()
;
VEC3
j2pr
=
n2
^
i
;
j2pr
.
normalize
()
;
// Rotation dans sens trigo dans le plan tangent autour de n (i1->i)
// REAL gamma1 = ((j1 * i) > 0 ? 1 : -1) * acos( std::max(std::min(1.0f, i1 * i ), -1.0f)) ; // angle positif ssi
REAL
gamma2
=
((
j2
*
i
)
>
0
?
1
:
-
1
)
*
acos
(
std
::
max
(
std
::
min
(
1.0
f
,
i2
*
i
),
-
1.0
f
))
;
// -PI/2 < angle(i,j1) < PI/2 ssi i*j1 > 0
// Rotation dans le sens trigo autour de l'axe i (n1->n)
// REAL alpha1 = ((n * j1pr) > 0 ? -1 : 1) * acos( std::max(std::min(1.0f, n * n1), -1.0f) ) ; // angle positif ssi
REAL
alpha2
=
((
n
*
j2pr
)
>
0
?
-
1
:
1
)
*
acos
(
std
::
max
(
std
::
min
(
1.0
f
,
n
*
n2
),
-
1.0
f
)
)
;
// PI/2 < angle(j1',n) < -PI/2 ssi j1'*n < 0
// assert (-0.01 < gamma1 && gamma1 < 0.01) ;
// assert (-0.01 < alpha1 && alpha1 < 0.01) ;
REAL
gamma1
=
REAL
(
0
)
;
REAL
alpha1
=
REAL
(
0
)
;
// Create and sum quadrics
m_quadricRGBfunctions
[
d
]
+=
QuadricRGBfunctions
<
REAL
>
(
this
->
m_attrV
[
d
],
gamma1
,
alpha1
)
;
m_quadricRGBfunctions
[
d
]
+=
QuadricRGBfunctions
<
REAL
>
(
this
->
m_attrV
[
dd
],
gamma2
,
alpha2
)
;
}
/************************************************************************************
* LIGHTFIELD QUADRIC METRIC : frame *
************************************************************************************/
...
...
@@ -106,8 +196,11 @@ bool Approximator_RGBfunctions<PFP>::init()
m_approxFrame
=
this
->
m_map
.
template
getAttribute
<
MATRIX33
>(
EDGE_ORBIT
,
"approx_frame"
)
;
m_quadricRGBfunctions
=
this
->
m_map
.
template
getAttribute
<
QuadricRGBfunctions
<
REAL
>
>
(
EDGE_ORBIT
,
"quadricRGBfunctions"
)
;
MapBrowserLinkedAuto
<
typename
PFP
::
MAP
>
mb
(
this
->
m_map
)
;
this
->
m_map
.
foreach_orbit
(
EDGE_ORBIT
,
mb
)
;
// create quadric embedding for computing and set them to 0
for
(
Dart
d
=
this
->
m_map
.
begin
()
;
d
!=
this
->
m_map
.
end
()
;
this
->
m_map
.
next
(
d
))
for
(
Dart
d
=
mb
.
begin
()
;
d
!=
mb
.
end
()
;
mb
.
next
(
d
))
m_quadricRGBfunctions
[
d
].
zero
()
;
// Check on embeddings
...
...
include/Algo/Decimation/selector.h
View file @
49e7e333
...
...
@@ -46,9 +46,11 @@ enum SelectorType
S_Random
,
S_EdgeLength
,
S_QEM
,
S_QEMml
,
S_MinDetail
,
S_Curvature
,
S_Lightfield
S_Lightfield
,
S_LightfieldHalf
}
;
...
...
@@ -228,6 +230,120 @@ public:
void
updateAfterCollapse
(
Dart
d2
,
Dart
dd2
)
;
}
;
template
<
typename
PFP
>
class
EdgeSelector_QEMml
:
public
EdgeSelector
<
PFP
>
{
public:
typedef
typename
PFP
::
MAP
MAP
;
typedef
typename
PFP
::
VEC3
VEC3
;
typedef
typename
PFP
::
REAL
REAL
;
private:
typedef
struct
{
typename
std
::
multimap
<
float
,
Dart
>::
iterator
it
;
bool
valid
;
static
std
::
string
CGoGNnameOfType
()
{
return
"QEMedgeInfo"
;
}
}
QEMedgeInfo
;
typedef
NoMathIOAttribute
<
QEMedgeInfo
>
EdgeInfo
;
AttributeHandler
<
EdgeInfo
>
edgeInfo
;
AttributeHandler
<
Quadric
<
REAL
>
>
quadric
;
std
::
multimap
<
float
,
Dart
>
edges
;
typename
std
::
multimap
<
float
,
Dart
>::
iterator
cur
;
Approximator
<
PFP
,
typename
PFP
::
VEC3
>*
m_positionApproximator
;
void
initEdgeInfo
(
Dart
d
)
;
void
updateEdgeInfo
(
Dart
d
,
bool
recompute
)
;
void
computeEdgeInfo
(
Dart
d
,
EdgeInfo
&
einfo
)
;
void
recomputeQuadric
(
const
Dart
d
,
const
bool
neighbours
=
false
)
;
Dart
rewind
(
const
Dart
d
)
;
public:
EdgeSelector_QEMml
(
MAP
&
m
,
typename
PFP
::
TVEC3
&
pos
,
std
::
vector
<
ApproximatorGen
<
PFP
>*>&
approx
,
const
FunctorSelect
&
select
=
SelectorTrue
())
:
EdgeSelector
<
PFP
>
(
m
,
pos
,
approx
,
select
)
{
edgeInfo
=
m
.
template
addAttribute
<
EdgeInfo
>(
EDGE_ORBIT
,
"edgeInfo"
)
;
quadric
=
m
.
template
addAttribute
<
Quadric
<
REAL
>
>
(
VERTEX_ORBIT
,
"QEMquadric"
)
;
}
~
EdgeSelector_QEMml
()
{
this
->
m_map
.
removeAttribute
(
quadric
)
;
this
->
m_map
.
removeAttribute
(
edgeInfo
)
;
}
SelectorType
getType
()
{
return
S_QEM
;
}
bool
init
()
;
bool
nextEdge
(
Dart
&
d
)
;
void
updateBeforeCollapse
(
Dart
d
)
;
void
updateAfterCollapse
(
Dart
d2
,
Dart
dd2
)
;
}
;
template
<
typename
PFP
>
class
HalfEdgeSelector_Lightfield
:
public
EdgeSelector
<
PFP
>
{
public:
typedef
typename
PFP
::
MAP
MAP
;
typedef
typename
PFP
::
VEC3
VEC3
;
typedef
typename
PFP
::
REAL
REAL
;
typedef
Geom
::
Matrix
<
3
,
3
,
REAL
>
MATRIX33
;
typedef
MATRIX33
FRAME
;
typedef
Geom
::
Matrix
<
3
,
6
,
REAL
>
MATRIX36
;
typedef
MATRIX36
RGBFUNCTIONS
;
private:
typedef
struct
{
typename
std
::
multimap
<
float
,
Dart
>::
iterator
it
;
bool
valid
;
static
std
::
string
CGoGNnameOfType
()
{
return
"LightfieldHalfEdgeInfo"
;
}
}
LightfieldHalfEdgeInfo
;
typedef
NoMathIOAttribute
<
LightfieldHalfEdgeInfo
>
HalfEdgeInfo
;
AttributeHandler
<
FRAME
>
m_frame
;
AttributeHandler
<
HalfEdgeInfo
>
halfEdgeInfo
;
AttributeHandler
<
Quadric
<
REAL
>
>
quadric
;
AttributeHandler
<
QuadricRGBfunctions
<
REAL
>
>
quadricRGBfunctions
;
std
::
multimap
<
float
,
Dart
>
halfEdges
;
typename
std
::
multimap
<
float
,
Dart
>::
iterator
cur
;
Approximator
<
PFP
,
VEC3
>*
m_positionApproximator
;
Approximator
<
PFP
,
FRAME
>*
m_frameApproximator
;
Approximator
<
PFP
,
RGBFUNCTIONS
>*
m_RGBfunctionsApproximator
;
void
initHalfEdgeInfo
(
Dart
d
)
;
void
updateHalfEdgeInfo
(
Dart
d
,
bool
recompute
)
;
void
computeHalfEdgeInfo
(
Dart
d
,
HalfEdgeInfo
&
einfo
)
;
void
recomputeQuadric
(
const
Dart
d
,
const
bool
neighbors
)
;
Dart
rewind
(
const
Dart
d
)
;
public:
HalfEdgeSelector_Lightfield
(
MAP
&
m
,
typename
PFP
::
TVEC3
&
pos
,
std
::
vector
<
ApproximatorGen
<
PFP
>*>&
approx
,
const
FunctorSelect
&
select
=
SelectorTrue
())
:
EdgeSelector
<
PFP
>
(
m
,
pos
,
approx
,
select
)
{
m_frame
=
m
.
template
getAttribute
<
FRAME
>(
VERTEX_ORBIT
,
"frame"
)
;
halfEdgeInfo
=
m
.
template
addAttribute
<
HalfEdgeInfo
>(
DART_ORBIT
,
"halfEdgeInfo"
)
;
quadric
=
m
.
template
addAttribute
<
Quadric
<
REAL
>
>
(
VERTEX_ORBIT
,
"QEMquadric"
)
;
quadricRGBfunctions
=
m
.
template
addAttribute
<
QuadricRGBfunctions
<
REAL
>
>
(
EDGE_ORBIT
,
"quadricRGBfunctions"
)
;
}
~
HalfEdgeSelector_Lightfield
()
{
this
->
m_map
.
removeAttribute
(
quadric
)
;
this
->
m_map
.
removeAttribute
(
quadricRGBfunctions
)
;
this
->
m_map
.
removeAttribute
(
halfEdgeInfo
)
;
}
SelectorType
getType
()
{
return
S_Lightfield
;
}
bool
init
()
;
bool
nextEdge
(
Dart
&
d
)
;
void
updateBeforeCollapse
(
Dart
d
)
;
void
updateAfterCollapse
(
Dart
d2
,
Dart
dd2
)
;
}
;
template
<
typename
PFP
>
class
EdgeSelector_Lightfield
:
public
EdgeSelector
<
PFP
>
{
...
...
include/Algo/Decimation/selector.hpp
View file @
49e7e333
...
...
@@ -404,9 +404,9 @@ void EdgeSelector_QEM<PFP>::updateAfterCollapse(Dart d2, Dart dd2)
do // - edges for which only the collapsibility must be re-tested
{
updateEdgeInfo(vit2, false) ;
updateEdgeInfo
(
m
.
phi1
(
vit2
),
false
)
;
updateEdgeInfo(m.phi1(vit2), false) ;
// OPTIM POSSIBLE : ne pas faire le 1er phi1(vit2) (car sera fait dans prochaine itération) ?
vit2 = m.alpha_1(vit2) ;
}
while
(
vit2
!=
stop
)
;
} while(vit2 != stop) ;
// OPTIM POSSIBLE : ne pas faire vit2 == stop (car déjà fait dans initEdgeInfo(vit)) ?
}
else
updateEdgeInfo(vit, true) ;
...
...
@@ -478,6 +478,537 @@ void EdgeSelector_QEM<PFP>::computeEdgeInfo(Dart d, EdgeInfo& einfo)
einfo.valid = true ;
}
/************************************************************************************
* QUADRIC ERROR METRIC (Memoryless version) *
************************************************************************************/
template <typename PFP>
bool EdgeSelector_QEMml<PFP>::init()
{
MAP& m = this->m_map ;
bool ok = false ;
for(typename std::vector<ApproximatorGen<PFP>*>::iterator it = this->m_approximators.begin();
it != this->m_approximators.end() && !ok;
++it)
{
if((*it)->getApproximatedAttributeName() == "position")
{
m_positionApproximator = reinterpret_cast<Approximator<PFP, VEC3>* >(*it) ;
ok = true ;
}
}
if(!ok)
return false ;
edges.clear() ;
CellMarker vMark(m, VERTEX_CELL) ;
for(Dart d = m.begin(); d != m.end(); m.next(d))
{
if(!vMark.isMarked(d))
{
Quadric<REAL> q ; // create one quadric
quadric[d] = q ; // per vertex
vMark.mark(d) ;
}
}
DartMarker mark(m) ;
for(Dart d = m.begin(); d != m.end(); m.next(d))
{
if(!mark.isMarked(d))
{
Dart d1 = m.phi1(d) ; // for each triangle,
Dart d_1 = m.phi_1(d) ; // initialize the quadric of the triangle
Quadric<REAL> q(this->m_position[d], this->m_position[d1], this->m_position[d_1]) ;
quadric[d] += q ; // and add the contribution of
quadric[d1] += q ; // this quadric to the ones
quadric[d_1] += q ; // of the 3 incident vertices
mark.markOrbit(FACE_ORBIT, d) ;
}
}
CellMarker eMark(m, EDGE_CELL) ;
for(Dart d = m.begin(); d != m.end(); m.next(d))
{
if(!eMark.isMarked(d))
{
initEdgeInfo(d) ; // init the edges with their optimal position
eMark.mark(d) ; // and insert them in the multimap according to their error
}
}
cur = edges.begin() ; // init the current edge to the first one
return true ;
}
template <typename PFP>
bool EdgeSelector_QEMml<PFP>::nextEdge(Dart& d)
{
if(cur == edges.end() || edges.empty())
return false ;
d = (*cur).second ;
return true ;
}
template <typename PFP>
void EdgeSelector_QEMml<PFP>::updateBeforeCollapse(Dart d)
{
MAP& m = this->m_map ;
EdgeInfo& edgeE = edgeInfo[d] ;
if(edgeE.valid)
edges.erase(edgeE.it) ;
edgeE = edgeInfo[m.phi1(d)] ;
if(edgeE.valid) // remove all
edges.erase(edgeE.it) ;
edgeE = edgeInfo[m.phi_1(d)] ; // the concerned edges
if(edgeE.valid)
edges.erase(edgeE.it) ;
// from the multimap
Dart dd = m.phi2(d) ;
if(dd != d)
{
edgeE = edgeInfo[m.phi1(dd)] ;
if(edgeE.valid)
edges.erase(edgeE.it) ;
edgeE = edgeInfo[m.phi_1(dd)] ;
if(edgeE.valid)
edges.erase(edgeE.it) ;
}
}
/**
* rewind until border (if any)
*/
// TODO : check & optimize
template <typename PFP>
Dart EdgeSelector_QEMml<PFP>::rewind(const Dart d) {
Dart dInit = d ;
do {
if (dInit == this->m_map.phi2(dInit)) // if border
break ; // stop
dInit = this->m_map.alpha_1(dInit) ;
} while (dInit != d) ;
return dInit ;
}
/**
* Update quadric of a vertex
* Discards quadrics of d and assigns freshly calculated
* quadrics depending on the actual planes surrounding d
* @param dart d
*/
template <typename PFP>
void EdgeSelector_QEMml<PFP>::recomputeQuadric(const Dart d, const bool neighbours) {
Dart dFront,dBack;
Dart dInit = rewind(d) ; // rewind until border (if any)
// Init Front
dFront = dInit;
quadric[d].zero();
do {
// Make step
dBack = dFront ;
dFront = this->m_map.alpha1(dFront);
if (neighbours)
recomputeQuadric(this->m_map.phi2(dFront), false) ;
if (dFront == this->m_map.phi2(dFront))
break ;
quadric[d] += Quadric<REAL>(this->m_position[d],this->m_position[this->m_map.phi2(dFront)],this->m_position[this->m_map.phi2(dBack)]);
} while(dFront != dInit);
}
template <typename PFP>
void EdgeSelector_QEMml<PFP>::updateAfterCollapse(Dart d2, Dart dd2)
{
MAP& m = this->m_map ;
// for local vertex and neighbors
recomputeQuadric(d2, true) ;
Dart vit = d2 ;
do
{
updateEdgeInfo(m.phi1(vit), true) ; // must recompute some edge infos in the
if(vit == d2 || vit == dd2) // neighborhood of the collapsed edge
initEdgeInfo(vit) ; // various optimizations are applied here by
else // treating differently :
updateEdgeInfo(vit, true) ;
Dart vit2 = m.alpha_1(m.phi1(vit)) ; // - edges for which the criteria must be recomputed
Dart stop = m.phi2(vit) ; // - edges that must be re-embedded
do // - edges for which only the collapsibility must be re-tested
{
updateEdgeInfo(vit2, true) ;
updateEdgeInfo(m.phi1(vit2), false) ;
vit2 = m.alpha_1(vit2) ; // OPTIM POSSIBLE : ne pas faire vit2 == stop car déjà fait dans init/updateEdgeInfo(vit)
} while(vit2 != stop) ;
vit = m.alpha1(vit) ;
} while(vit != d2) ;
cur = edges.begin() ; // set the current edge to the first one
}
template <typename PFP>
void EdgeSelector_QEMml<PFP>::initEdgeInfo(Dart d)
{
MAP& m = this->m_map ;
EdgeInfo einfo ;
if(m.edgeCanCollapse(d))
computeEdgeInfo(d, einfo) ;
else
einfo.valid = false ;
edgeInfo[d] = einfo ;
}
template <typename PFP>
void EdgeSelector_QEMml<PFP>::updateEdgeInfo(Dart d, bool recompute)
{
MAP& m = this->m_map ;
EdgeInfo& einfo = edgeInfo[d] ;
if(recompute)
{
if(einfo.valid)
edges.erase(einfo.it) ; // remove the edge from the multimap
if(m.edgeCanCollapse(d))
computeEdgeInfo(d, einfo) ;
else
einfo.valid = false ;
}
else
{
if(m.edgeCanCollapse(d))
{ // if the edge can be collapsed now
if(!einfo.valid) // but it was not before
computeEdgeInfo(d, einfo) ;
}
else
{ // if the edge cannot be collapsed now
if(einfo.valid) // and it was before
{
edges.erase(einfo.it) ;
einfo.valid = false ;
}
}
}
}
template <typename PFP>
void EdgeSelector_QEMml<PFP>::computeEdgeInfo(Dart d, EdgeInfo& einfo)
{
MAP& m = this->m_map ;
Dart dd = m.phi2(d) ;
Quadric<REAL> quad ;
quad += quadric[d] ; // compute the sum of the
quad += quadric[dd] ; // two vertices quadrics
m_positionApproximator->approximate(d) ;
REAL err = quad(m_positionApproximator->getApprox(d)) ;
einfo.it = edges.insert(std::make_pair(err, d)) ;
einfo.valid = true ;
}
/************************************************************************************
* HALFEDGESELECTOR LIGHTFIELD *
************************************************************************************/