]> Creatis software - FrontAlgorithms.git/blob - lib/fpa/Base/MarksInterfaceWithCollisions.hxx
12309317bb63389ab4c445593e59095a5559e49b
[FrontAlgorithms.git] / lib / fpa / Base / MarksInterfaceWithCollisions.hxx
1 // =========================================================================
2 // @author Leonardo Florez Valencia
3 // @email florez-l@javeriana.edu.co
4 // =========================================================================
5
6 #ifndef __fpa__Base__MarksInterfaceWithCollisions__hxx__
7 #define __fpa__Base__MarksInterfaceWithCollisions__hxx__
8
9 #include <queue>
10
11 // -------------------------------------------------------------------------
12 template< class _TVertex >
13 bool fpa::Base::MarksInterfaceWithCollisions< _TVertex >::
14 StopAtOneFront( ) const
15 {
16   return( this->m_StopAtOneFront );
17 }
18
19 // -------------------------------------------------------------------------
20 template< class _TVertex >
21 void fpa::Base::MarksInterfaceWithCollisions< _TVertex >::
22 StopAtOneFrontOn( )
23 {
24   this->SetStopAtOneFront( true );
25 }
26
27 // -------------------------------------------------------------------------
28 template< class _TVertex >
29 void fpa::Base::MarksInterfaceWithCollisions< _TVertex >::
30 StopAtOneFrontOff( )
31 {
32   this->SetStopAtOneFront( false );
33 }
34
35 // -------------------------------------------------------------------------
36 template< class _TVertex >
37 void fpa::Base::MarksInterfaceWithCollisions< _TVertex >::
38 SetStopAtOneFront( bool v )
39 {
40   if( this->m_StopAtOneFront != v )
41   {
42     this->m_StopAtOneFront = v;
43     if( this->m_Filter != NULL )
44       this->m_Filter->Modified( );
45
46   } // fi
47 }
48
49 // -------------------------------------------------------------------------
50 template< class _TVertex >
51 fpa::Base::MarksInterfaceWithCollisions< _TVertex >::
52 MarksInterfaceWithCollisions( itk::ProcessObject* filter )
53   : Superclass( filter ),
54     m_StopAtOneFront( false ),
55     m_NumberOfFronts( 0 )
56 {
57 }
58
59 // -------------------------------------------------------------------------
60 template< class _TVertex >
61 fpa::Base::MarksInterfaceWithCollisions< _TVertex >::
62 ~MarksInterfaceWithCollisions( )
63 {
64 }
65
66 // -------------------------------------------------------------------------
67 template< class _TVertex >
68 void fpa::Base::MarksInterfaceWithCollisions< _TVertex >::
69 _InitMarks( unsigned long nSeeds )
70 {
71   this->Superclass::_InitMarks( nSeeds );
72   this->m_NumberOfFronts = nSeeds;
73   TCollision coll( TVertex( ), false );
74   TCollisionsRow row( this->m_NumberOfFronts, coll );
75   this->m_Collisions.clear( );
76   this->m_Collisions.resize( this->m_NumberOfFronts, row );
77 }
78
79 // -------------------------------------------------------------------------
80 template< class _TVertex >
81 bool fpa::Base::MarksInterfaceWithCollisions< _TVertex >::
82 _Collisions( const TVertex& a, const TVertex& b )
83 {
84   unsigned long ma = this->_GetMark( a );
85   unsigned long mb = this->_GetMark( b );
86   if( ma == mb || ma == 0 || mb == 0 )
87     return( false );
88
89   // Mark collision, if it is new
90   ma--; mb--;
91   bool ret = false;
92   bool exists = this->m_Collisions[ ma ][ mb ].second;
93   exists     &= this->m_Collisions[ mb ][ ma ].second;
94   if( !exists )
95   {
96     this->m_Collisions[ ma ][ mb ].first = a;
97     this->m_Collisions[ ma ][ mb ].second = true;
98     this->m_Collisions[ mb ][ ma ].first = b;
99     this->m_Collisions[ mb ][ ma ].second = true;
100
101     // Update number of fronts
102     unsigned long count = 0;
103     std::vector< bool > m( this->m_NumberOfSeeds, false );
104     std::queue< unsigned long > q;
105     q.push( 0 );
106     while( !q.empty( ) )
107     {
108       unsigned long f = q.front( );
109       q.pop( );
110
111       if( m[ f ] )
112         continue;
113       m[ f ] = true;
114       count++;
115
116       for( unsigned int n = 0; n < this->m_NumberOfSeeds; ++n )
117         if( this->m_Collisions[ f ][ n ].second && !m[ n ] )
118           q.push( n );
119
120     } // elihw
121     this->m_NumberOfFronts = this->m_NumberOfSeeds - count + 1;
122
123   } // fi
124   return(
125     this->m_StopAtOneFront &&
126     this->m_NumberOfSeeds > 1 &&
127     this->m_NumberOfFronts == 1
128     );
129 }
130
131 #endif // __fpa__Base__MarksInterfaceWithCollisions__hxx__
132
133 // eof - $RCSfile$