/* * trackermanager implementation * * Copyright (C) ZhangLiang, YuanJun, Li Wei, Li Ming, Andreas Nuechter * * Released under the GPL version 3. * */ /** * @file * @brief Main programm for dynamic Velodyne SLAM * * @author Andreas Nuechter. Jacobs University Bremen, Germany * @author YuanJun, Wuhan University, China * @author ZhangLiang, Wuhan University, China * @author Li Wei, Wuhan University, China * @author Li Ming, Wuhan University, China */ #include #include #include #include #ifdef _MSC_VER #include #else #include #endif #include "slam6d/scan.h" #include "slam6d/globals.icc" #include "veloslam/color_util.h" #include "veloslam/veloscan.h" #include "veloslam/trackermanager.h" #include "veloslam/debugview.h" #include "veloslam/kalmanfilter.h" #include "veloslam/lap.h" #define KG 35 #define BIGNUM 100000 int sliding_window_size = 6; int current_sliding_window_pos =0; Trajectory VelodyneTrajectory; VeloScan * g_pfirstScan; float constant_static_or_moving = 20.0; int GetScanID_in_SlidingWindow(int absNO, int current_pos, int window_size) { int firstNO=-1; // relative scanID absolute scanID // absNO (6,7,8,9) current_pos(6,7,8,9) window_size =6 #ifdef NO_SLIDING_WINDOW firstNO = absNO; #else if( (absNO >=(current_pos - window_size) ) && (absNO <= current_pos) ) { firstNO =absNO - (current_pos - window_size ); } else { //in first scans firstNO = -1; } if(current_pos < window_size) { //in first scans firstNO = absNO; } #endif // cout << " absNO " << absNO << " firstNO "<0) { radiusDiff=fabs(tracker.statusList.back().radius-glu.radius); thetaDiff=fabs(tracker.statusList.back().theta-glu.theta); sizeDiff =abs(tracker.statusList.back().size-glu.size); shapeDiff =fabs( fabs(tracker.statusList.back().size_x-glu.size_x) + fabs(tracker.statusList.back().size_y-glu.size_y) + fabs(tracker.statusList.back().size_z-glu.size_z) ); positionDiff = sqrt( (tracker.statusList.back().avg_x -glu.avg_x)*(tracker.statusList.back().avg_x -glu.avg_x) + (tracker.statusList.back().avg_z -glu.avg_z)*(tracker.statusList.back().avg_z -glu.avg_z) ) ; } value= radiusDiff*1.0 + thetaDiff*1.0 + sizeDiff*0.8 + shapeDiff*0.8 + positionDiff * 0.3 ; if(value < minValue) { minValue=value; minID=i; temp=glu; flag=true; } } } // find matched tracker. if (flag) { tracker.kalmanFilter.stateUpdate(temp,rollAngle,delta_Pos); tracker.kalmanFilter.timeUpdate(); // movestate=tracker.kalmanFilter.GetCurrentState(); // cout<<"The tracker with trackerID:"<::iterator it; int trackNO =0; for(it=tracks.begin() ; it!=tracks.end();it++ ) { Tracker &tracker=*it; trackNO ++; if (!(tracker.missMatch)) { matchID=MatchTrackers(scanRef,tracker,KG); } else { matchID=MatchTrackers(scanRef,tracker,1.5*KG); } if(matchID==-1) { // log miss times of tracker tracker.missMatch=true; tracker.missedTime++; // cout << "missing tracker" << tracker.trackerID // <<" times " <=0 ) { scanRef.scanClusterFeatureArray[matchID].trackNO = trackNO; clusterFeature &glu=scanRef.scanClusterFeatureArray[matchID]; cluster &gluData=scanRef.scanClusterArray[matchID]; glu.frameNO= scanRef.scanid; glu.selfID = matchID; // save feature tracker.statusList.push_back(glu); tracker.dataList.push_back(gluData); tracker.matchClusterID=matchID; tracker.missMatch=false; clusterStatus[matchID].Matched=true; // cout << "Match tracker" << tracker.trackerID // <<" size of " <::iterator it; cout<<" tracker list : "<::iterator it; int trackNO =0; for(it=tracks.begin() ; it!=tracks.end();) { Tracker &tracker=*it; #ifndef NO_SLIDING_WINDOW if (!tracker.statusList.empty()) { deque::iterator Iter1; deque::iterator Iter2; vector::iterator Iter3; Iter1=tracker.statusList.begin(); Iter2=tracker.dataList.begin(); Iter3=tracker.moveStateList.begin(); do { clusterFeature &tempClu=*Iter1; if(tempClu.frameNO current_sliding_window_pos) { //cout<<"trackerID: "<::iterator Iter; for (Iter=tracks.begin();Iter!=tracks.end();Iter++) { Tracker temp=*Iter; temp.TrackerReset(); } tracks.clear(); return; } int TrackerManager::CalculateTrackersFeature(vector allScans, int currentNO ,int windowsize) { int i,j,k,colorIdx; float movement; list::iterator it; int n; for(it=tracks.begin(); it!=tracks.end(); it++) { Tracker &tracker=*it; tracker.moving_distance = 0.0; int size=tracker.statusList.size(); if ( size <2 ) { continue; } movement =0; n=0; for ( i=0;i=current_sliding_window_pos - sliding_window_size&&glu2.frameNO <=current_sliding_window_pos) { movement += sqrt( (p1.x -p2.x)*(p1.x -p2.x)+(p1.z -p2.z)*(p1.z -p2.z) ); n++; } #else movement += sqrt( (p1.x -p2.x)*(p1.x -p2.x)+(p1.z -p2.z)*(p1.z -p2.z) ); #endif // cout << " tracker no" << tracker.matchClusterID <<" " // << p1.x <<" " << p2.x <<" " //<< p1.y <<" " << p2.y <<" " //<< p1.z <<" " << p2.z <<" " << movement <<" " << endl; } #ifdef NO_SLIDING_WINDOW if (n!=0) { tracker.moving_distance=movement/n; } else { tracker.moving_distance=0; } #else tracker.moving_distance = movement/(size-1); #endif } return 0; } int TrackerManager::MarkClassifiyTrackersResult(vector allScans, int currentNO ,int windowsize) { int i,j,k,colorIdx; float movement; list::iterator it; // mark all objets type such as moving or static for(it=tracks.begin(); it!=tracks.end(); it++) { int currentScanNo =0; Tracker &tracker=*it; int size=tracker.statusList.size(); // no tracking all for slam // for tracking classifiation //not transfrom to scan if (size < 3) { for(i=0;iscanClusterFeatureArray[glu1.selfID]; cluster &realgclu = CurrentScan->scanClusterArray[glu1.selfID]; realglu1.clusterType = CLUSTER_TYPE_STATIC_OBJECT; for(j =0; j< realgclu.size() ; ++j) { cellFeature &gcF = *(realgclu[j]); gcF.cellType = CELL_TYPE_STATIC; } } continue; } for(i=0;iscanClusterFeatureArray[glu1.selfID]; cluster &realgclu = CurrentScan->scanClusterArray[glu1.selfID]; if(tracker.moving_distance < constant_static_or_moving) { realglu1.clusterType = CLUSTER_TYPE_STATIC_OBJECT; for(j =0; j< realgclu.size() ; ++j) { cellFeature &gcF = *(realgclu[j]); gcF.cellType = CELL_TYPE_STATIC; } } else { realglu1.clusterType = CLUSTER_TYPE_MOVING_OBJECT; for(j =0; j< realgclu.size() ; ++j) { cellFeature &gcF = *(realgclu[j]); gcF.cellType = CELL_TYPE_MOVING; } } } } return 0; } int TrackerManager::ClassifiyTrackersObjects(vector allScans, int currentNO ,int windowsize) { CalculateTrackersFeature(allScans, currentNO, windowsize); MarkClassifiyTrackersResult(allScans, currentNO , windowsize); return 0; } int TrackerManager::UpdateClustersPoistioninTrackers() { int i,j; list::iterator it; for(it=tracks.begin() ; it!=tracks.end();it++ ) { Tracker &tracker=*it; /* firstNO = GetScanID_in_SlidingWindow(glu1.frameNO, current_sliding_window_pos, sliding_window_size); secondNO = GetScanID_in_SlidingWindow(glu2.frameNO, current_sliding_window_pos, sliding_window_size); if(firstNO <0 || secondNO< 0 ) continue; Scan *firstScan = (Scan *)g_pfirstScan; Scan *CurrentScan = allScans[firstNO]; Scan *CurrentScanNext = allScans[secondNO]; double deltaMat[16]; double deltaMatNext[16]; GetCurrecntdelteMat(*CurrentScan , *firstScan, deltaMat); GetCurrecntdelteMat(*CurrentScanNext , *firstScan, deltaMatNext); p1.x = glu1.avg_x; p1.y= glu1.avg_y;p1.z=glu1.avg_z; p1text.x= glu1.avg_x+150; p1text.y= glu1.avg_y+80; p1text.z=glu1.avg_z+50; p2.x = glu2.avg_x; p2.y= glu2.avg_y; p2.z=glu2.avg_z; p2text.x= glu2.avg_x+150; p2text.y= glu2.avg_y+80; p2text.z=glu2.avg_z+50; */ } return 0; } void TrackerManager::GetTwoScanRoll(Scan *CurrentScan,Scan *preScan)//??? { double tempMat[16],deltaMat[16]; M4inv(preScan->get_transMat(), tempMat); MMult(CurrentScan->get_transMat(), tempMat,deltaMat); Matrix4ToEuler(deltaMat,delta_Theta,delta_Pos); //cout<<"delta_Theta: "<trackSize?clusterSize:trackSize; } else { maxSize=clusterSize; } CMatrix costMatrix(maxSize,maxSize); int i=0,j,k; double costValue; float radiusDiff; float thetaDiff; float sizeDiff; float positionDiff; CMatrix standardDeviation(2,2),measurementErro(2,1); Measurement predictMeasurement; bool IsSmaller1,IsSmaller2; float kg; list::iterator it; for(it=tracks.begin(); it!=tracks.end(); it++) { Tracker &tracker=*it; predictMeasurement=tracker.kalmanFilter.GetPredictMeasurement(rollAngle,delta_Pos); standardDeviation=tracker.kalmanFilter.CalMeasureDeviation(); if (tracker.missMatch) { kg=1.5*KG; } else { kg=KG; } k=0; for(j=0;j::iterator it; for(it=tracks.begin() ; it!=tracks.end();it++) { Tracker &tracker=*it; trackNO ++; trackerIndex++; if (missFlag[trackerIndex]) { tracker.missMatch=true; tracker.missedTime++; } else { int clusterID=rowsol[trackerIndex]; int matchID=clusterIndex[clusterID]; //cout<<"TrackerID: "<