00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013 #include "Image/Image.H"
00014 #include "Image/Pixels.H"
00015 #include "Image/ImageSet.H"
00016 #include "Util/Timer.H"
00017 #include "Util/Types.H"
00018 #include "Util/log.H"
00019
00020 void BeoSubQtMainForm::init(const nub::soft_ref<BeoSubOneBal>& sub,
00021 const nub::soft_ref<Beowulf>& beo,
00022 const nub::soft_ref<BeoSubTaskDecoder>& decoder,
00023 const nub::soft_ref<ColorTracker>& tracker1,
00024 const nub::soft_ref<ColorTracker>& tracker2,
00025 const nub::soft_ref<BeoSubCanny>& detector)
00026 {
00027 DIR *dir;
00028 struct dirent *entry;
00029 int size = 50;
00030 float hp, hi, hd;
00031 float pp, pi, pd;
00032 float dp, di, dd;
00033 char buffer[size], fileName[20];
00034
00035 counterUp = counterFront = counterDown = 0;
00036 if (getcwd(buffer, size) == NULL) PLFATAL("error in getcwd");
00037 if((dir = opendir(buffer)) == NULL)
00038 printf("open dir error");
00039 else
00040 {
00041 while((entry = readdir(dir)) !=NULL)
00042 {
00043 if(entry->d_name[0] != '.')
00044 {
00045 strcpy(fileName, entry->d_name);
00046 QString qs(fileName);
00047 if(qs.contains("top") > 0)
00048 {
00049 topFiles.push_back(fileName);
00050 qs.replace("top", "");
00051 qs.replace(".txt", "");
00052 if(qs.toInt() > counterUp)
00053 counterUp = qs.toInt();
00054 }
00055 if(qs.contains("front") > 0)
00056 {
00057 frontFiles.push_back(fileName);
00058 qs.replace("front", "");
00059 qs.replace(".txt", "");
00060 if(qs.toInt() > counterFront)
00061 counterFront = qs.toInt();
00062 }
00063 if(qs.contains("bottom") > 0)
00064 {
00065 bottomFiles.push_back(fileName);
00066 qs.replace("bottom", "");
00067 qs.replace(".txt", "");
00068 if(qs.toInt() > counterDown)
00069 counterDown = qs.toInt();
00070 }
00071 }
00072 }
00073 }
00074 if(counterUp != 0)
00075 counterUp++;
00076 if(counterFront != 0)
00077 counterFront++;
00078 if(counterDown != 0)
00079 counterDown++;
00080 joyflag = true;
00081 itsSub = sub; itsBeo = beo; itsTracker1 = tracker1; itsTracker2 = tracker2; itsDecoder = decoder; itsDetector = detector;
00082 FrontBDisplay->setText(QString(convertToString(0)));
00083 RearBDisplay->setText(QString(convertToString(0)));
00084 BsDisplay->setText(QString(convertToString(0)));
00085
00086 LTDisplay->setText(QString(convertToString(0)));
00087 RTDisplay->setText(QString(convertToString(0)));
00088 TsDisplay->setText(QString(convertToString(0)));
00089
00090 TurnDisplay->setText(QString(convertToString(0)));
00091 TiltDisplay->setText(QString(convertToString(0)));
00092 savePIDgain = fopen("PIDgains.pid", "r");
00093 if (fscanf(savePIDgain, "%f %f %f\n", &hp, &hi, &hd) != 3) LFATAL("fscanf error");
00094 if (fscanf(savePIDgain, "%f %f %f\n", &pp, &pi, &pd) != 3) LFATAL("fscanf error");
00095 if (fscanf(savePIDgain, "%f %f %f\n", &dp, &di, &dd) != 3) LFATAL("fscanf error");
00096 HeadingP->setText(QString(sformat("%f",hp)));
00097 HeadingI->setText(QString(sformat("%f",hi)));
00098 HeadingD->setText(QString(sformat("%f",hd)));
00099 PitchP->setText(QString(sformat("%f",pp)));
00100 PitchI->setText(QString(sformat("%f",pi)));
00101 PitchD->setText(QString(sformat("%f",pd)));
00102 DepthP->setText(QString(sformat("%f",dp)));
00103 DepthI->setText(QString(sformat("%f",di)));
00104 DepthD->setText(QString(sformat("%f",dd)));
00105 fclose(savePIDgain);
00106 startTimer(1000);
00107
00108 }
00109
00110 void BeoSubQtMainForm::togglePic()
00111 {
00112 takePic = !takePic;
00113 }
00114 void BeoSubQtMainForm::savePIDvalue()
00115 {
00116 savePIDgain = fopen("PIDgains.pid", "w");
00117 fprintf(savePIDgain, "%f %f %f\n", HeadingP->text().toFloat(), HeadingI->text().toFloat(), HeadingD->text().toFloat());
00118 fprintf(savePIDgain, "%f %f %f\n", PitchP->text().toFloat(), PitchI->text().toFloat(), PitchD->text().toFloat());
00119 fprintf(savePIDgain, "%f %f %f", DepthP->text().toFloat(), DepthI->text().toFloat(), DepthD->text().toFloat());
00120 fclose(savePIDgain);
00121 }
00122 void BeoSubQtMainForm::HeadingPID_toggled()
00123 {
00124 if(HeadingPID->isOn())
00125 {
00126 itsSub->setHeadingPgain(HeadingP->text().toFloat());
00127 itsSub->setHeadingIgain(HeadingI->text().toFloat());
00128 itsSub->setHeadingDgain(HeadingD->text().toFloat());
00129 itsSub->useHeadingPID(true);
00130 savePIDvalue();
00131 }
00132 else
00133 itsSub->useHeadingPID(false);
00134 }
00135
00136 void BeoSubQtMainForm::PitchPID_toggled()
00137 {
00138 if(PitchPID->isOn())
00139 {
00140 itsSub->setPitchPgain(PitchP->text().toFloat());
00141 itsSub->setPitchIgain(PitchI->text().toFloat());
00142 itsSub->setPitchDgain(PitchD->text().toFloat());
00143 itsSub->usePitchPID(true);
00144 savePIDvalue();
00145 }
00146 else
00147 itsSub->usePitchPID(false);
00148 }
00149
00150 void BeoSubQtMainForm::DepthPID_toggled()
00151 {
00152 if(DepthPID->isOn())
00153 {
00154 itsSub->setDepthPgain(DepthP->text().toFloat());
00155 itsSub->setDepthIgain(DepthI->text().toFloat());
00156 itsSub->setDepthDgain(DepthD->text().toFloat());
00157 itsSub->useDepthPID(true);
00158 savePIDvalue();
00159 }
00160 else
00161 itsSub->useDepthPID(false);
00162 }
00163
00164 void BeoSubQtMainForm::KILL_toggled()
00165 {
00166 if(KILL->isOn())
00167 itsSub->useKillSwitch(true);
00168 else
00169 itsSub->useKillSwitch(false);
00170 }
00171
00172 void BeoSubQtMainForm::turnopen_return()
00173 {
00174 Angle a = double(to->text().toDouble());
00175 itsSub->turnOpen(a, true);
00176 }
00177
00178 void BeoSubQtMainForm::advance_return()
00179 {
00180 itsSub->advanceRel(lineEditAdvance->text().toFloat());
00181 }
00182
00183 void BeoSubQtMainForm::strafe_return()
00184 {
00185 itsSub->strafeRel(lineEditStrafe->text().toFloat());
00186 }
00187
00188 void BeoSubQtMainForm::resetAtt_return()
00189 {
00190 LERROR("unimplemented");
00191 }
00192
00193 void BeoSubQtMainForm::FrontBallast_valueChanged(int val)
00194 {
00195
00196 itsSub->setFrontBallast(float(val)/100.0F);
00197 FrontBDisplay->setText(QString(convertToString(val)));
00198 }
00199
00200 void BeoSubQtMainForm::RearBallast_valueChanged(int val)
00201 {
00202
00203 itsSub->setRearBallast(float(val)/100.0F);
00204 RearBDisplay->setText(QString(convertToString(val)));
00205 }
00206
00207 void BeoSubQtMainForm::LThruster_valueChanged(int val)
00208 {
00209 float rt, lt;
00210 itsSub->getThrusters(lt, rt);
00211
00212 itsSub->thrust(float(val)/100.0F, rt);
00213 LTDisplay->setText(QString(convertToString(val)));
00214 }
00215
00216 void BeoSubQtMainForm::RThuster_valueChanged(int val)
00217 {
00218 float rt, lt;
00219 itsSub->getThrusters(lt, rt);
00220
00221 itsSub->thrust(lt, float(val)/100.0F);
00222 RTDisplay->setText(QString(convertToString(val)));
00223 }
00224
00225 void BeoSubQtMainForm::Thrusters_valueChanged(int val)
00226 {
00227
00228 itsSub->thrust(float(val)/100.0F, float(val)/100.0F);
00229 LTScroll->setValue(val);
00230 RTScroll->setValue(val);
00231 TsDisplay->setText(QString(convertToString(val)));
00232 }
00233
00234 void BeoSubQtMainForm::dive_valueChanged(int val)
00235 {
00236 itsSub->diveAbs(float(val)/10.0F, false);
00237 BsDisplay->setText(QString(convertToString(val)));
00238 }
00239
00240 void BeoSubQtMainForm::Orient_valueChanged(int val)
00241 {
00242 Angle a = double(val);
00243 itsSub->turnAbs(a, false);
00244 TurnDisplay->setText(QString(convertToString(val)));
00245 }
00246
00247 void BeoSubQtMainForm::Pitch_valueChanged(int val)
00248 {
00249 Angle a = double(val);
00250 itsSub->pitchAbs(a, false);
00251 TiltDisplay->setText(QString(convertToString(val)));
00252 }
00253
00254 void BeoSubQtMainForm::timerEvent( QTimerEvent *e )
00255 {
00256 displayFunc();
00257 }
00258
00259 void BeoSubQtMainForm::saveImageLog(const char* name, int count)
00260 {
00261 FILE *f;
00262 float lt,rt;
00263 std::string s;
00264 itsSub->getThrusters(lt, rt);
00265 s = sformat("%s%06d.txt", name, count);
00266
00267 f = fopen(s.c_str(), "w");
00268 fprintf(f, "%s%06d.png\t", name, count);
00269 fprintf(f, "%f\t",itsSub->getHeading().getVal());
00270 fprintf(f, "%f\t",itsSub->getPitch().getVal());
00271 fprintf(f, "%f\t",itsSub->getRoll().getVal());
00272 fprintf(f, "%f\t",itsSub->getDepth());
00273 fprintf(f, "%f\t",itsSub->getFrontBallast());
00274 fprintf(f, "%f\t",itsSub->getRearBallast());
00275 fprintf(f, "%f\t",lt);
00276 fprintf(f, "%f\t",rt);
00277 fprintf(f, "-1000 -1000\t");
00278 fprintf(f, "%f", itsSub->getTime());
00279
00280
00281
00282
00283
00284
00285
00286 fprintf(f, "\n");
00287 fclose(f);
00288
00289 }
00290
00291 void BeoSubQtMainForm::saveImageUp()
00292 {
00293
00294 Raster::WriteRGB( imup, sformat("top%06d.png", counterUp) );
00295 topFiles.push_back(sformat("top%06d", counterUp));
00296
00297
00298 saveImageLog("top", counterUp);
00299 counterUp++;
00300 }
00301
00302 void BeoSubQtMainForm::saveImageFront()
00303 {
00304
00305 Raster::WriteRGB( imfront, sformat("front%06d.png", counterFront) );
00306 frontFiles.push_back(sformat("front%06d", counterFront));
00307
00308
00309 saveImageLog("front", counterFront);
00310 counterFront++;
00311 }
00312
00313 void BeoSubQtMainForm::saveImageDown()
00314 {
00315
00316 Raster::WriteRGB( imdown, sformat("bottom%06d.png", counterDown) );
00317 bottomFiles.push_back(sformat("bottom%06d", counterDown));
00318
00319
00320 saveImageLog("bottom", counterDown);
00321 counterDown++;
00322 }
00323
00324 void BeoSubQtMainForm::taskGate(){
00325 printf("You wish this were implemented\n");
00326 }
00327
00328 void BeoSubQtMainForm::taskDecode()
00329 {
00330 ImageSet< PixRGB<byte> > inStream;
00331 Image< PixRGB<byte> > img;
00332 int NAVG = 20; Timer tim; uint64 t[NAVG]; int frame = 0;
00333 float avg2 = 0.0;
00334
00335 for(int i = 0; i < 100; i++){
00336 tim.reset();
00337
00338 img = itsSub->grabImage(BEOSUBCAMFRONT);
00339 inStream.push_back(img);
00340
00341 uint64 t0 = tim.get();
00342 t[frame % NAVG] = tim.get();
00343 t0 = t[frame % NAVG] - t0;
00344
00345 if (frame % NAVG == 0 && frame > 0)
00346 {
00347 uint64 avg = 0ULL; for (int i = 0; i < NAVG; i ++) avg += t[i];
00348 avg2 = 1000.0F / float(avg) * float(NAVG);
00349 }
00350 frame ++;
00351 }
00352
00353 itsDecoder->setupDecoder("Red", false);
00354 itsDecoder->runDecoder(inStream, avg2);
00355 float hertz = itsDecoder->calculateHz();
00356 printf("\n\nFound Red with %f Hz\n\n", hertz);
00357 }
00358
00359 void BeoSubQtMainForm::taskA()
00360 {
00361 int counter = 0;
00362 while(counter > 8 && itsSub->getDepth() < 3.0){
00363 if(itsSub->affineSIFT(BEOSUBCAMDOWN, itsSub->itsVOtaskAdown)){
00364 itsSub->diveAbs(3.0);
00365 }
00366 }
00367
00368
00369
00370
00371
00372
00373
00374
00375
00376
00377
00378
00379
00380
00381
00382
00383
00384
00385
00386
00387
00388
00389
00390
00391
00392
00393
00394
00395
00396
00397 }
00398
00399 void BeoSubQtMainForm::taskB(){
00400 if(itsSub->TaskB())
00401 printf("\n\nFINISHED TASK B!\n\n");
00402 else
00403 printf("faild TASK B\n");
00404 }
00405
00406 void BeoSubQtMainForm::taskC(){
00407
00408 }
00409
00410 void BeoSubQtMainForm::stopAll()
00411 {
00412
00413 itsSub->thrust(0, 0);
00414 itsSub->setFrontBallast(0.0);
00415 itsSub->setRearBallast(0.0);
00416 FrontBScroll->setValue(0);
00417 RearBScroll->setValue(0);
00418 DiveScroll->setValue(0);
00419 LTScroll->setValue(0);
00420 RTScroll->setValue(0);
00421 TsScroll->setValue(0);
00422 }
00423
00424 void BeoSubQtMainForm::matchAndDirect()
00425 {
00426 Image< PixRGB<byte> > img = imdown;
00427 BeoSubDB* db = new BeoSubDB;
00428 db->initializeDatabase(bottomFiles, "bottomDB.txt");
00429 VisualObjectDB vdb;
00430 if(!vdb.loadFrom("bottomVDB.txt")){
00431 printf("Must create Visual Object Database befirehand\n");
00432 return;
00433 }
00434 rutz::shared_ptr<VisualObject> vo(new VisualObject("matching.png", "matching.png", imdown));
00435 std::vector< rutz::shared_ptr<VisualObjectMatch> > matches;
00436 const uint nmatches = vdb.getObjectMatches(vo, matches, VOMA_KDTREEBBF);
00437
00438 if(nmatches == 0U){
00439 printf("No match found\n");
00440 return;
00441 }
00442 rutz::shared_ptr<VisualObject> obj = matches[0]->getVoTest();
00443 std::string foundName(obj->getName().c_str());
00444
00445 uint idx = foundName.rfind('.'); foundName = foundName.substr(0, idx);
00446 foundName = foundName + ".txt";
00447
00448 printf("Found match %s with score %f\n", foundName.c_str(), matches[0]->getScore());
00449 MappingData foundMD = db->getMappingData(foundName);
00450 MappingData goalMD = db->getMappingData("TaskA.txt");
00451
00452 Attitude directions;
00453 float distance = 0.0;
00454 db->getDirections(foundMD, goalMD, directions, distance);
00455
00456 printf("\n\nThe needed depth is %f, heading is %f, and distance is %f\n\n", directions.depth, directions.heading.getVal(), distance);
00457 return;
00458 }
00459
00460 void BeoSubQtMainForm::parseMessage(TCPmessage& rmsg)
00461 {
00462 float yAxis = 0.0;
00463 float xAxis = 0.0;
00464 float xL=0.0F, xR=0.0F;
00465 float yL=0.0F, yR=0.0F;
00466 int button1 = 0;
00467 int button2 = 0;
00468 int button3 = 0;
00469
00470
00471
00472 Image<float> in = rmsg.getElementFloatIma();
00473
00474
00475 yAxis = in.getVal(0);
00476
00477 xAxis = in.getVal(1);
00478
00479
00480 button1 = (int)in.getVal(3);
00481
00482 button2 = (int)in.getVal(4);
00483
00484 button3 = (int)in.getVal(5);
00485
00486 if( yAxis > 0 )
00487 {
00488
00489 yL = 1.0F - 1.0F/32767 * yAxis; yR = 1.0F - 1.0F/32767 * yAxis;
00490 joyflag =true;
00491 }
00492 else if(yAxis < 0)
00493 {
00494
00495 yL = -1.0F - 1.0F/32767*yAxis; yR = -1.0F - 1.0F/32767*yAxis;
00496 joyflag = false;
00497 }
00498 else if(yAxis == 0)
00499 {
00500 if(joyflag)
00501 {
00502 yL = 1.0F; yR = 1.0F;
00503 }
00504 else
00505 {
00506 yL = -1.0F; yR = -1.0F;
00507 }
00508 }
00509 if( xAxis >0 )
00510 {
00511
00512 xL = -1.0F + 1.0F/32767*xAxis; xR = 1.0F - 1.0F/32767*xAxis;
00513 }
00514 else if(xAxis < 0)
00515 {
00516
00517 xL = 1.0 + 1.0/32767*xAxis; xR = -1.0 - 1.0/32767*xAxis;
00518 }
00519
00520 if(xR == 0.0F && xL == 0.0F)
00521 {
00522 itsSub->thrust(yL, yR);
00523 LTDisplay->setText(QString(sformat("%.3f", yL)));
00524 RTDisplay->setText(QString(sformat("%.3f", yR)));
00525 }
00526 else if(yR == 0.0F && yL == 0.0F)
00527 {
00528 itsSub->thrust(xL, xR);
00529 LTDisplay->setText(QString(sformat("%.3f", xL)));
00530 RTDisplay->setText(QString(sformat("%.3f", xR)));
00531 }
00532 else
00533 {
00534 itsSub->thrust( xL+yL / 2.0F, xR+yR / 2.0F);
00535 LTDisplay->setText(QString(sformat("%.3f", xL+yL / 2.0F)));
00536 RTDisplay->setText(QString(sformat("%.3f", xR+yR / 2.0F)));
00537 }
00538 if(button1 == 1.0F)
00539 saveImageUp();
00540 else if(button2 == 1.0F)
00541 saveImageFront();
00542 else if(button3 == 1.0F)
00543 saveImageDown();
00544
00545 }
00546
00547 void BeoSubQtMainForm::displayFunc()
00548 {
00549 Image< PixRGB<byte> > img;
00550 QPixmap qpixm;
00551 float lt,rt;
00552 FILE *f;
00553 char temp[50];
00554 int tempNum;
00555
00556 f = fopen("/proc/acpi/thermal_zone/THRM/temperature", "r");
00557 if (f == NULL)
00558 CPUtemp->setText(QString("can't find the file"));
00559 else
00560 {
00561 if (fscanf(f, "%s%d", temp, &tempNum) != 2) LFATAL("fscanf error");
00562 CPUtemp->setText(QString(convertToString(tempNum)));
00563 fclose(f);
00564 }
00565
00566 if(itsSub->targetReached())
00567 indicator->setText(QString("On Target"));
00568 else
00569 indicator->setText(QString("Homing"));
00570
00571
00572 imup = itsSub->grabImage(BEOSUBCAMUP);
00573 qpixm = convertToQPixmap(imup);
00574 ImagePixmapLabel1->setPixmap( qpixm );
00575
00576 imfront = itsSub->grabImage(BEOSUBCAMFRONT);
00577 qpixm = convertToQPixmap(imfront);
00578 ImagePixmapLabel2->setPixmap( qpixm );
00579
00580 imdown = itsSub->grabImage(BEOSUBCAMDOWN);
00581 qpixm = convertToQPixmap(imdown);
00582 ImagePixmapLabel3->setPixmap( qpixm );
00583
00584 itsSub->getThrusters(lt, rt);
00585
00586 LineEdit1->setText(QString(sformat("%.3f", itsSub->getRoll().getVal())));
00587 LineEdit2->setText(QString(sformat("%.3f", itsSub->getPitch().getVal())));
00588 LineEdit3->setText(QString(sformat("%.3f", itsSub->getHeading().getVal())));
00589 LineEdit4->setText(QString(sformat("%.3f", itsSub->getDepth())));
00590
00591 LineEdit1_2->setText(QString(sformat("%.3f", itsSub->getTargetAttitude().roll.getVal())));
00592 LineEdit2_2->setText(QString(sformat("%.3f", itsSub->getTargetAttitude().pitch.getVal())));
00593 LineEdit3_2->setText(QString(sformat("%.3f", itsSub->getTargetAttitude().heading.getVal())));
00594 LineEdit4_2->setText(QString(sformat("%.3f", itsSub->getTargetAttitude().depth)));
00595
00596 LineEdit11->setText(QString(sformat("%.3f", itsSub->getFrontBallast())));
00597 LineEdit12->setText(QString(sformat("%.3f", itsSub->getRearBallast())));
00598 LineEdit15->setText(QString(sformat("%.3f", lt)));
00599 LineEdit16->setText(QString(sformat("%.3f", rt)));
00600 topfilename->setText(QString(sformat("top%06d.png",counterUp)));
00601 frontfilename->setText(QString(sformat("front%06d.png",counterFront)));
00602 bottomfilename->setText(QString(sformat("bottom%06d.png",counterDown)));
00603
00604 if (itsBeo.isValid())
00605 {
00606 int32 rframe, raction, rnode = -1;
00607 for (int ii = 0; ii < 30; ii ++)
00608 {
00609 if (itsBeo->receive(rnode, rmsg, rframe, raction))
00610 parseMessage(rmsg);
00611 }
00612 }
00613 if(takePic)
00614 {
00615 saveImageUp();
00616 saveImageFront();
00617 saveImageDown();
00618 }
00619
00620 }
00621
00622 void BeoSubQtMainForm::keyPressEvent( QKeyEvent *event )
00623 {
00624 switch(event->key())
00625 {
00626
00627 case Key_Space:
00628
00629 itsSub->thrust(0.0, 0.0);
00630 break;
00631
00632 case Key_A:
00633 if(itsSub->getFrontBallast() + 0.05F <= 0.95F)
00634 itsSub->setFrontBallast(itsSub->getFrontBallast() + 0.05F);
00635 else
00636 itsSub->setFrontBallast(1.0F);
00637
00638 if(itsSub->getRearBallast() + 0.05F <= 0.95F)
00639 itsSub->setRearBallast(itsSub->getRearBallast() + 0.05F);
00640 else
00641 itsSub->setRearBallast(1.0F);
00642
00643 break;
00644
00645 case Key_Q:
00646 if(itsSub->getFrontBallast() - 0.05F >= 0.05F)
00647 itsSub->setFrontBallast(itsSub->getFrontBallast() - 0.05F);
00648 else
00649 itsSub->setFrontBallast(0.0F);
00650
00651 if(itsSub->getRearBallast() - 0.05F >= 0.05F)
00652 itsSub->setRearBallast(itsSub->getRearBallast() - 0.05F);
00653 else
00654 itsSub->setRearBallast(0.0F);
00655 break;
00656
00657 case Key_Z:
00658 saveImageUp();
00659 break;
00660 case Key_X:
00661 saveImageFront();
00662 break;
00663 case Key_C:
00664 saveImageDown();
00665 break;
00666
00667
00668 case Key_I:
00669 itsSub->thrust (1.0, 1.0);
00670 break;
00671
00672 case Key_J:
00673 itsSub->thrust(-1.0, 1.0);
00674 break;
00675
00676 case Key_K:
00677 itsSub->thrust(-1.0,-1.0);
00678 break;
00679
00680 case Key_L:
00681 itsSub->thrust( 1.0,-1.0);
00682 break;
00683 }
00684 }
00685
00686 void BeoSubQtMainForm::keyReleaseEvent( QKeyEvent *event )
00687 {
00688 switch(event->key())
00689 {
00690 case Key_I:
00691 case Key_J:
00692 case Key_K:
00693 case Key_L:
00694 itsSub->thrust(0.0,0.0);
00695 break;
00696 }
00697 }