00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #ifndef WTHREADEDTRACKINGFUNCTION_TEST_H
00026 #define WTHREADEDTRACKINGFUNCTION_TEST_H
00027
00028 #include <vector>
00029
00030 #include <cxxtest/TestSuite.h>
00031
00032 #include "../../common/WLogger.h"
00033 #include "../WThreadedTrackingFunction.h"
00034
00035
00036
00037
00038
00039
00040 class WTrackingUtilityTest : public CxxTest::TestSuite
00041 {
00042
00043 typedef WTrackingUtilityTest This;
00044
00045 public:
00046
00047
00048
00049 void setUp()
00050 {
00051 WLogger::startup();
00052 }
00053
00054
00055
00056
00057
00058 void testBoundary()
00059 {
00060 WVector3d x( 0.707, 0.707, 0.0 );
00061 WVector3d y( -0.707, 0.707, 0.0 );
00062 WVector3d z( 0.0, 0.0, 1.0 );
00063 x = normalize( x );
00064 y = normalize( y );
00065
00066 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 0.0, 1.0, 0.0 ) );
00067
00068 TS_ASSERT( ds );
00069 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00070
00071 WVector3d v( 1.0, 0.0, 0.0 );
00072 v += x * -0.5;
00073 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00074 v[ 0 ] += 0.5 * TRACKING_EPS;
00075 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00076 v[ 2 ] -= 2.0 * TRACKING_EPS;
00077 v[ 1 ] += 1.6 * TRACKING_EPS;
00078 TS_ASSERT( !wtracking::WTrackingUtility::onBoundary( g, v ) );
00079
00080 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 0.5;
00081 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00082 v[ 0 ] -= 0.6 * TRACKING_EPS;
00083 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00084 v[ 2 ] += 1.5 * TRACKING_EPS;
00085 v[ 1 ] += 2.6 * TRACKING_EPS;
00086 TS_ASSERT( !wtracking::WTrackingUtility::onBoundary( g, v ) );
00087
00088 v = WVector3d( 1.0, 0.0, 0.0 ) + y * 1.77 + z * 0.65;
00089 TS_ASSERT( !wtracking::WTrackingUtility::onBoundary( g, v ) );
00090
00091 v = WVector3d( 1.0, 0.0, 0.0 ) + y * 1.0 + z * 0.65;
00092 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00093
00094 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 3.5 + y * 1.77 + z * 0.65;
00095 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00096
00097 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 1.5 + y * 1.77 + z * 0.65;
00098 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00099
00100 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 3.9 + y * 5.0 + z * 0.65;
00101 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00102
00103 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 2.3 + y * 7.73 + z * 3.75;
00104 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00105
00106 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 3.4 + y * 1.77 + z * 6.75;
00107 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00108
00109 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 3.5 + y * 5.0 + z * 0.65;
00110 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00111 v[ 1 ] -= 0.7 * TRACKING_EPS;
00112 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, v ) );
00113 v[ 0 ] += 3.5 * TRACKING_EPS;
00114 v[ 1 ] += 0.7 * TRACKING_EPS;
00115 TS_ASSERT( !wtracking::WTrackingUtility::onBoundary( g, v ) );
00116
00117 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 1.2 + y * 7.9 + z * 5.3;
00118 TS_ASSERT( !wtracking::WTrackingUtility::onBoundary( g, v ) );
00119 }
00120
00121
00122
00123
00124 void testGetDistanceToBoundary()
00125 {
00126 WVector3d x( 0.707, 0.707, 0.0 );
00127 WVector3d y( -0.707, 0.707, 0.0 );
00128 WVector3d z( 0.0, 0.0, 1.0 );
00129 x = normalize( x );
00130 y = normalize( y );
00131
00132 WVector3d v( 1.0, 0.0, 0.0 );
00133
00134 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 0.0, 1.0, 0.0 ) );
00135 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00136
00137 TS_ASSERT_DELTA( wtracking::WTrackingUtility::getDistanceToBoundary( g, v, x ), 0.5, TRACKING_EPS );
00138 TS_ASSERT_DELTA( wtracking::WTrackingUtility::getDistanceToBoundary( g, v, y ), 1.0, TRACKING_EPS );
00139 TS_ASSERT_DELTA( wtracking::WTrackingUtility::getDistanceToBoundary( g, v, z ), 0.75, TRACKING_EPS );
00140
00141 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 0.5;
00142 TS_ASSERT_THROWS( wtracking::WTrackingUtility::getDistanceToBoundary( g, v, x ), WException );
00143
00144 v -= x * 2.0 * TRACKING_EPS;
00145 TS_ASSERT_DELTA( wtracking::WTrackingUtility::getDistanceToBoundary( g, v, x ), 2.0 * TRACKING_EPS, TRACKING_EPS );
00146
00147 v = WVector3d( 2.9741, 3.527, 1.992 );
00148 WVector3d dir( 3, 4, -2.003 );
00149 dir = normalize( dir );
00150 double t = wtracking::WTrackingUtility::getDistanceToBoundary( g, v, dir );
00151 WVector3d res = v + dir * t;
00152 TS_ASSERT( wtracking::WTrackingUtility::onBoundary( g, res ) );
00153
00154 v = WVector3d( 1.0, 0.0, 0.0 ) + x * 3.75 + y * 6.65 + z * 5.59;
00155 TS_ASSERT_DELTA( wtracking::WTrackingUtility::getDistanceToBoundary( g, v, y ), 0.35, TRACKING_EPS );
00156 }
00157
00158
00159
00160
00161
00162 void testFollowToNextVoxel()
00163 {
00164 {
00165 WVector3d x( 0.707, 0.707, 0.0 );
00166 WVector3d y( -0.707, 0.707, 0.0 );
00167 WVector3d z( 0.0, 0.0, 1.0 );
00168 x = normalize( x );
00169 y = normalize( y );
00170
00171 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 0.0, 1.0, 0.0 ) );
00172 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00173
00174 wtracking::WTrackingUtility::JobType j;
00175
00176 j.first = WVector3d( 1.0, 0.0, 0.0 ) + ( x + y + z ) * ( wlimits::FLT_EPS + 0.7 );
00177 j.second = x;
00178 TS_ASSERT( g->encloses( j.first ) );
00179
00180 WVector3d v = j.first;
00181
00182 TS_ASSERT( wtracking::WTrackingUtility::followToNextVoxel( ds, j, boost::bind( &This::simpleDirFunc, this, _1, _2 ) ) );
00183 TS_ASSERT( !wtracking::WTrackingUtility::onBoundary( g, j.first ) );
00184 TS_ASSERT( g->encloses( j.first ) );
00185 v += x * 0.8;
00186 TS_ASSERT_DELTA( length( j.first - v ), 0.0, 2.0 * TRACKING_EPS );
00187 }
00188 }
00189
00190 private:
00191
00192
00193
00194
00195
00196
00197 WVector3d simpleDirFunc( wtracking::WTrackingUtility::DataSetPtr, wtracking::WTrackingUtility::JobType const& )
00198 {
00199 WVector3d v( 1.0, 1.0, 0.0 );
00200 v = normalize( v );
00201 return v;
00202 }
00203
00204
00205
00206
00207
00208
00209
00210
00211 boost::shared_ptr< WDataSetSingle > buildTestData( WVector3d data )
00212 {
00213 WVector3d x( 0.707, 0.707, 0.0 );
00214 WVector3d y( -0.707, 0.707, 0.0 );
00215 WVector3d z( 0.0, 0.0, 1.0 );
00216
00217 x = normalize( x );
00218 y = normalize( y );
00219
00220 y *= 2.0;
00221 z *= 1.5;
00222
00223 WMatrix< double > mat( 4, 4 );
00224 mat.makeIdentity();
00225 mat( 0, 0 ) = x[ 0 ];
00226 mat( 1, 0 ) = x[ 1 ];
00227 mat( 2, 0 ) = x[ 2 ];
00228 mat( 0, 1 ) = y[ 0 ];
00229 mat( 1, 1 ) = y[ 1 ];
00230 mat( 2, 1 ) = y[ 2 ];
00231 mat( 0, 2 ) = z[ 0 ];
00232 mat( 1, 2 ) = z[ 1 ];
00233 mat( 2, 2 ) = z[ 2 ];
00234 mat( 0, 3 ) = 1.0;
00235
00236 WGridTransformOrtho t( mat );
00237 boost::shared_ptr< WGrid > g( new WGridRegular3D( 5, 5, 5, t ) );
00238
00239 data = normalize( data );
00240
00241 boost::shared_ptr< std::vector< double > > v = boost::shared_ptr< std::vector< double > >( new std::vector< double > ( 5 * 5 * 5 * 3 ) );
00242 for( std::size_t k = 0; k < 5 * 5 * 5; ++k )
00243 {
00244 v->at( 3 * k + 0 ) = data[ 0 ];
00245 v->at( 3 * k + 1 ) = data[ 1 ];
00246 v->at( 3 * k + 2 ) = data[ 2 ];
00247 }
00248
00249 boost::shared_ptr< WValueSetBase > vs( new WValueSet< double >( 1, 3, v, W_DT_DOUBLE ) );
00250 return boost::shared_ptr< WDataSetSingle >( new WDataSetSingle( vs, g ) );
00251 }
00252 };
00253
00254
00255
00256
00257
00258
00259 class WThreadedTrackingFunctionTest : public CxxTest::TestSuite
00260 {
00261
00262 typedef WThreadedTrackingFunctionTest This;
00263
00264 public:
00265
00266
00267
00268 void testIndexInitialization()
00269 {
00270 std::vector< int > v0;
00271 std::vector< int > v1;
00272 std::size_t numSeeds = 1;
00273 std::size_t seedsPerPosition = 1;
00274
00275 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 1.0, 0.0, 0.0 ), 5 );
00276 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00277 TS_ASSERT( g );
00278
00279 {
00280 wtracking::WThreadedTrackingFunction::IndexType i;
00281 i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition );
00282
00283
00284 TS_ASSERT_EQUALS( i.m_done, false );
00285 TS_ASSERT_EQUALS( i.m_offset, 1.0 );
00286 TS_ASSERT_EQUALS( i.m_pos[ 0 ], 1 );
00287 TS_ASSERT_EQUALS( i.m_pos[ 1 ], 1 );
00288 TS_ASSERT_EQUALS( i.m_pos[ 2 ], 1 );
00289 TS_ASSERT_EQUALS( i.m_pos[ 3 ], 0 );
00290 TS_ASSERT_EQUALS( i.m_min[ 0 ], 1 );
00291 TS_ASSERT_EQUALS( i.m_min[ 1 ], 1 );
00292 TS_ASSERT_EQUALS( i.m_min[ 2 ], 1 );
00293 TS_ASSERT_EQUALS( i.m_min[ 3 ], 0 );
00294 TS_ASSERT_EQUALS( i.m_max[ 0 ], 4 );
00295 TS_ASSERT_EQUALS( i.m_max[ 1 ], 4 );
00296 TS_ASSERT_EQUALS( i.m_max[ 2 ], 4 );
00297 TS_ASSERT_EQUALS( i.m_max[ 3 ], 1 );
00298 }
00299 {
00300 v0.resize( 3 );
00301 v1.resize( 3 );
00302 v0[ 0 ] = 1;
00303 v0[ 1 ] = 2;
00304 v0[ 2 ] = 1;
00305 v1[ 0 ] = 3;
00306 v1[ 1 ] = 3;
00307 v1[ 2 ] = 4;
00308 numSeeds = 4;
00309 seedsPerPosition = 3;
00310
00311 wtracking::WThreadedTrackingFunction::IndexType i;
00312 TS_ASSERT_THROWS_NOTHING( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ) );
00313
00314
00315 TS_ASSERT_EQUALS( i.m_done, false );
00316 TS_ASSERT_EQUALS( i.m_offset, 0.25 );
00317 TS_ASSERT_EQUALS( i.m_pos[ 0 ], 4 );
00318 TS_ASSERT_EQUALS( i.m_pos[ 1 ], 8 );
00319 TS_ASSERT_EQUALS( i.m_pos[ 2 ], 4 );
00320 TS_ASSERT_EQUALS( i.m_pos[ 3 ], 0 );
00321 TS_ASSERT_EQUALS( i.m_min[ 0 ], 4 );
00322 TS_ASSERT_EQUALS( i.m_min[ 1 ], 8 );
00323 TS_ASSERT_EQUALS( i.m_min[ 2 ], 4 );
00324 TS_ASSERT_EQUALS( i.m_min[ 3 ], 0 );
00325 TS_ASSERT_EQUALS( i.m_max[ 0 ], 12 );
00326 TS_ASSERT_EQUALS( i.m_max[ 1 ], 12 );
00327 TS_ASSERT_EQUALS( i.m_max[ 2 ], 16 );
00328 TS_ASSERT_EQUALS( i.m_max[ 3 ], 3 );
00329 }
00330 {
00331
00332 wtracking::WThreadedTrackingFunction::IndexType i;
00333 v0[ 0 ] = -1;
00334 TS_ASSERT_THROWS( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ), WException );
00335 v0[ 0 ] = 0;
00336 v1[ 1 ] = 5;
00337 TS_ASSERT_THROWS( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ), WException );
00338 }
00339 }
00340
00341
00342
00343
00344 void testIndexIncrement()
00345 {
00346 std::vector< int > v0;
00347 std::vector< int > v1;
00348 std::size_t numSeeds = 1;
00349 std::size_t seedsPerPosition = 1;
00350
00351 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 1.0, 0.0, 0.0 ), 5 );
00352 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00353 TS_ASSERT( g );
00354
00355 {
00356 wtracking::WThreadedTrackingFunction::IndexType i;
00357 TS_ASSERT_THROWS_NOTHING( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ) );
00358
00359 for( int j = 0; j < 27; ++j )
00360 {
00361 TS_ASSERT( !i.done() );
00362 ++i;
00363 }
00364 TS_ASSERT( i.done() );
00365 }
00366 {
00367 numSeeds = 4;
00368 wtracking::WThreadedTrackingFunction::IndexType i;
00369 TS_ASSERT_THROWS_NOTHING( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ) );
00370
00371 for( int j = 0; j < 27 * 64; ++j )
00372 {
00373 TS_ASSERT( !i.done() );
00374 ++i;
00375 }
00376 TS_ASSERT( i.done() );
00377 }
00378 {
00379 seedsPerPosition = 3;
00380 wtracking::WThreadedTrackingFunction::IndexType i;
00381 TS_ASSERT_THROWS_NOTHING( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ) );
00382
00383 for( int j = 0; j < 27 * 64 * 3; ++j )
00384 {
00385 TS_ASSERT( !i.done() );
00386 ++i;
00387 }
00388 TS_ASSERT( i.done() );
00389 }
00390 {
00391 v0.resize( 3, 1 );
00392 v1.resize( 3 );
00393 v1[ 0 ] = 4;
00394 v1[ 1 ] = 3;
00395 v1[ 2 ] = 4;
00396 wtracking::WThreadedTrackingFunction::IndexType i;
00397 TS_ASSERT_THROWS_NOTHING( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ) );
00398
00399 for( int j = 0; j < 18 * 64 * 3; ++j )
00400 {
00401 TS_ASSERT( !i.done() );
00402 ++i;
00403 }
00404 TS_ASSERT( i.done() );
00405 }
00406 }
00407
00408
00409
00410
00411 void testIndexToJob()
00412 {
00413 WVector3d x( 0.707, 0.707, 0.0 );
00414 WVector3d y( -0.707, 0.707, 0.0 );
00415 WVector3d z( 0.0, 0.0, 1.0 );
00416 x = normalize( x );
00417 y = normalize( y );
00418 y *= 2.0;
00419 z *= 1.5;
00420
00421 std::vector< int > v0;
00422 std::vector< int > v1;
00423 std::size_t numSeeds = 2;
00424 std::size_t seedsPerPosition = 1;
00425
00426 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 1.0, 0.0, 0.0 ), 5 );
00427 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00428 TS_ASSERT( g );
00429
00430 {
00431 wtracking::WThreadedTrackingFunction::IndexType i;
00432 TS_ASSERT_THROWS_NOTHING( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ) );
00433
00434 wtracking::WThreadedTrackingFunction::JobType job = i.job();
00435 WVector3d v = g->getOrigin() + 0.75 * x + 0.75 * y + 0.75 * z;
00436
00437 std::cout << g->getOrigin() << std::endl;
00438
00439 TS_ASSERT_DELTA( v[ 0 ], job.first[ 0 ], TRACKING_EPS );
00440 TS_ASSERT_DELTA( v[ 1 ], job.first[ 1 ], TRACKING_EPS );
00441 TS_ASSERT_DELTA( v[ 2 ], job.first[ 2 ], TRACKING_EPS );
00442
00443 v += 0.5 * z;
00444 ++i;
00445 job = i.job();
00446 TS_ASSERT_DELTA( v[ 0 ], job.first[ 0 ], TRACKING_EPS );
00447 TS_ASSERT_DELTA( v[ 1 ], job.first[ 1 ], TRACKING_EPS );
00448 TS_ASSERT_DELTA( v[ 2 ], job.first[ 2 ], TRACKING_EPS );
00449
00450 for( int k = 0; k < 6; ++k )
00451 {
00452 ++i;
00453 }
00454 v += 0.5 * y;
00455 job = i.job();
00456 TS_ASSERT_DELTA( v[ 0 ], job.first[ 0 ], TRACKING_EPS );
00457 TS_ASSERT_DELTA( v[ 1 ], job.first[ 1 ], TRACKING_EPS );
00458 TS_ASSERT_DELTA( v[ 2 ], job.first[ 2 ], TRACKING_EPS );
00459
00460 for( int k = 0; k < 36; ++k )
00461 {
00462 ++i;
00463 }
00464 v += 0.5 * x;
00465 job = i.job();
00466 TS_ASSERT_DELTA( v[ 0 ], job.first[ 0 ], TRACKING_EPS );
00467 TS_ASSERT_DELTA( v[ 1 ], job.first[ 1 ], TRACKING_EPS );
00468 TS_ASSERT_DELTA( v[ 2 ], job.first[ 2 ], TRACKING_EPS );
00469
00470 TS_ASSERT_EQUALS( job.second[ 0 ], 0.0 );
00471 TS_ASSERT_EQUALS( job.second[ 1 ], 0.0 );
00472 TS_ASSERT_EQUALS( job.second[ 2 ], 0.0 );
00473 }
00474 {
00475 numSeeds = 4;
00476 seedsPerPosition = 11;
00477 wtracking::WThreadedTrackingFunction::IndexType i;
00478 TS_ASSERT_THROWS_NOTHING( i = wtracking::WThreadedTrackingFunction::IndexType( g, v0, v1, numSeeds, seedsPerPosition ) );
00479
00480 wtracking::WThreadedTrackingFunction::JobType job;
00481 WVector3d v = g->getOrigin() + 0.625 * x + 0.625 * y + 0.625 * z;
00482 for( int k = 0; k < 11; ++k )
00483 {
00484 job = i.job();
00485 TS_ASSERT_DELTA( v[ 0 ], job.first[ 0 ], TRACKING_EPS );
00486 TS_ASSERT_DELTA( v[ 1 ], job.first[ 1 ], TRACKING_EPS );
00487 TS_ASSERT_DELTA( v[ 2 ], job.first[ 2 ], TRACKING_EPS );
00488 ++i;
00489 }
00490 }
00491 }
00492
00493
00494
00495
00496 void testInstantiation()
00497 {
00498 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 1.0, 0.0, 0.0 ), 5 );
00499 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00500 TS_ASSERT( g );
00501
00502 TS_ASSERT_THROWS_NOTHING(
00503 wtracking::WThreadedTrackingFunction w( ds,
00504 boost::bind( &This::dirFunc, this, _1, _2, WVector3d( 1.0, 0.0, 0.0 ) ),
00505 boost::bind( &wtracking::WTrackingUtility::followToNextVoxel, _1, _2, _3 ),
00506 boost::bind( &This::fibVis, this, _1 ),
00507 boost::bind( &This::pntVis, this, _1 ) ) );
00508 }
00509
00510
00511
00512
00513 void testGetJob()
00514 {
00515 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 1.0, 0.0, 0.0 ), 7 );
00516 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00517 TS_ASSERT( g );
00518
00519 wtracking::WThreadedTrackingFunction w( ds, boost::bind( &This::dirFunc, this, _1, _2, WVector3d( 1.0, 0.0, 0.0 ) ),
00520 boost::bind( &wtracking::WTrackingUtility::followToNextVoxel, _1, _2, _3 ),
00521 boost::bind( &This::fibVis, this, _1 ),
00522 boost::bind( &This::pntVis, this, _1 ) );
00523 wtracking::WThreadedTrackingFunction::JobType job;
00524 for( int i = 0; i < 125; ++i )
00525 {
00526 TS_ASSERT( w.getJob( job ) );
00527 }
00528 TS_ASSERT( !w.getJob( job ) );
00529 }
00530
00531
00532
00533
00534 void testCompute()
00535 {
00536 WVector3d x( 0.707, 0.707, 0.0 );
00537 WVector3d y( -0.707, 0.707, 0.0 );
00538 WVector3d z( 0.0, 0.0, 1.0 );
00539 x = normalize( x );
00540 y = normalize( y );
00541
00542 boost::shared_ptr< WDataSetSingle > ds = buildTestData( WVector3d( 1.0, 0.0, 0.0 ), 7 );
00543 boost::shared_ptr< WGridRegular3D > g = boost::shared_dynamic_cast< WGridRegular3D >( ds->getGrid() );
00544 TS_ASSERT( g );
00545 {
00546 wtracking::WThreadedTrackingFunction w( ds, boost::bind( &This::dirFunc, this, _1, _2, x ),
00547 boost::bind( &wtracking::WTrackingUtility::followToNextVoxel, _1, _2, _3 ),
00548 boost::bind( &This::fibVis, this, _1 ),
00549 boost::bind( &This::pntVis, this, _1 ) );
00550 wtracking::WThreadedTrackingFunction::JobType job;
00551 m_points.getWriteTicket()->get() = 0;
00552 w.getJob( job );
00553 w.compute( ds, job );
00554 TS_ASSERT_EQUALS( m_points.getReadTicket()->get(), 7 );
00555 }
00556 {
00557 wtracking::WThreadedTrackingFunction w( ds, boost::bind( &This::dirFunc, this, _1, _2, y ),
00558 boost::bind( &wtracking::WTrackingUtility::followToNextVoxel, _1, _2, _3 ),
00559 boost::bind( &This::fibVis, this, _1 ),
00560 boost::bind( &This::pntVis, this, _1 ) );
00561 wtracking::WThreadedTrackingFunction::JobType job;
00562 m_points.getWriteTicket()->get() = 0;
00563 w.getJob( job );
00564 w.compute( ds, job );
00565 TS_ASSERT_EQUALS( m_points.getReadTicket()->get(), 7 );
00566 }
00567 }
00568
00569 private:
00570
00571
00572
00573
00574
00575
00576
00577
00578 boost::shared_ptr< WDataSetSingle > buildTestData( WVector3d data, int n )
00579 {
00580 WVector3d x( 0.707, 0.707, 0.0 );
00581 WVector3d y( -0.707, 0.707, 0.0 );
00582 WVector3d z( 0.0, 0.0, 1.0 );
00583 x = normalize( x );
00584 y = normalize( y );
00585 y *= 2.0;
00586 z *= 1.5;
00587
00588 WMatrix< double > mat( 4, 4 );
00589 mat.makeIdentity();
00590 mat( 0, 0 ) = x[ 0 ];
00591 mat( 1, 0 ) = x[ 1 ];
00592 mat( 2, 0 ) = x[ 2 ];
00593 mat( 0, 1 ) = y[ 0 ];
00594 mat( 1, 1 ) = y[ 1 ];
00595 mat( 2, 1 ) = y[ 2 ];
00596 mat( 0, 2 ) = z[ 0 ];
00597 mat( 1, 2 ) = z[ 1 ];
00598 mat( 2, 2 ) = z[ 2 ];
00599 mat( 0, 3 ) = 1.0;
00600
00601 WGridTransformOrtho t( mat );
00602 boost::shared_ptr< WGrid > g( new WGridRegular3D( n, n, n, t ) );
00603
00604 data = normalize( data );
00605
00606 boost::shared_ptr< std::vector< double > > v = boost::shared_ptr< std::vector< double > >( new std::vector< double >( n * n * n * 3 ) );
00607 for( std::size_t k = 0; k < static_cast< std::size_t >( n * n * n ); ++k )
00608 {
00609 v->at( 3 * k + 0 ) = data[ 0 ];
00610 v->at( 3 * k + 1 ) = data[ 1 ];
00611 v->at( 3 * k + 2 ) = data[ 2 ];
00612 }
00613
00614 boost::shared_ptr< WValueSetBase > vs( new WValueSet< double >( 1, 3, v, W_DT_DOUBLE ) );
00615 return boost::shared_ptr< WDataSetSingle >( new WDataSetSingle( vs, g ) );
00616 }
00617
00618
00619
00620
00621
00622
00623
00624
00625
00626 WVector3d dirFunc( wtracking::WThreadedTrackingFunction::DataSetPtr,
00627 wtracking::WThreadedTrackingFunction::JobType const& j,
00628 WVector3d d )
00629 {
00630 if( dot( j.second, d ) > 0.0 )
00631 {
00632 return d;
00633 }
00634 else
00635 {
00636 return d * -1.0;
00637 }
00638 }
00639
00640
00641
00642
00643 void fibVis( std::vector< WVector3d > const& )
00644 {
00645 }
00646
00647
00648
00649
00650 void pntVis( WVector3d const& )
00651 {
00652 ++m_points.getWriteTicket()->get();
00653 }
00654
00655
00656 WSharedObject< std::size_t > m_points;
00657 };
00658
00659 #endif // WTHREADEDTRACKINGFUNCTION_TEST_H