88 m_pOldFinalConf[i] = 0;
90 m_pOldSensorConf[i] = 0;
93 m_pPredictedConf[i] = 0;
96 m_nNumParticles = nNumParticles;
97 m_nNumAnnealingRuns = nNumAnnealingRuns;
98 m_nPredictionMode = nPredictionMode;
99 m_dVarianceFactor = 1.0;
101 const int nNumThreads = omp_get_num_procs();
105 m_pSobelXImageLeft, m_pSobelXImageRight, m_pSobelYImageLeft, m_pSobelYImageRight);
107 m_pObjectFinderLeft =
new CObjectFinder();
108 m_pObjectFinderRight =
new CObjectFinder();
109 m_pdTrBallPosXLeft =
new double[m_nMaxTrBallRegions];
110 m_pdTrBallPosXRight =
new double[m_nMaxTrBallRegions];
111 m_pdTrBallPosYLeft =
new double[m_nMaxTrBallRegions];
112 m_pdTrBallPosYRight =
new double[m_nMaxTrBallRegions];
113 m_pdTrBallRadiusLeft =
new double[m_nMaxTrBallRegions];
114 m_pdTrBallRadiusRight =
new double[m_nMaxTrBallRegions];
130 delete m_pHSVImageLeft;
131 delete m_pHSVImageRight;
136 delete m_pSobelXImageLeft;
137 delete m_pSobelXImageRight;
138 delete m_pSobelYImageLeft;
139 delete m_pSobelYImageRight;
140 delete m_pTempGrayImage1;
141 delete m_pTempGrayImage2;
142 delete m_pTempGrayImage3;
143 delete m_pTempGrayImage4;
144 delete m_pTempGrayImage5;
145 delete m_pTempGrayImage6;
149 delete[] m_pFinalConf;
150 delete[] m_pOldFinalConf;
151 delete[] m_pSensorConf;
152 delete[] m_pOldSensorConf;
154 delete[] m_pOldPFConf;
155 delete[] m_pPredictedConf;
157 delete m_pParticleFilter;
159 delete m_pObjectFinderLeft;
160 delete m_pObjectFinderRight;
161 delete[] m_pdTrBallPosXLeft;
162 delete[] m_pdTrBallPosXRight;
163 delete[] m_pdTrBallPosYLeft;
164 delete[] m_pdTrBallPosYRight;
165 delete[] m_pdTrBallRadiusLeft;
166 delete[] m_pdTrBallRadiusRight;
176 angles.y = asin(mat.r3);
177 angles.x = atan2((-mat.r6), (mat.r9));
178 angles.z = atan2((-mat.r2), (mat.r1));
183 void CHandLocalisation::LocaliseHand(
const CByteImage* pNewCamImageLeft,
const CByteImage* pNewCamImageRight,
const Vec3d vPositionFromSensors,
const Mat3d mOrientationFromSensors,
const double* pSensorConfigFingers,
double* pEstimatedConfig,
double& dConfidenceRating)
186 Vec3d vRotationAngles;
188 pSensorConfig[0] = vPositionFromSensors.x;
189 pSensorConfig[1] = vPositionFromSensors.y;
190 pSensorConfig[2] = vPositionFromSensors.z;
191 pSensorConfig[3] = vRotationAngles.x;
192 pSensorConfig[4] = vRotationAngles.y;
193 pSensorConfig[5] = vRotationAngles.z;
196 pSensorConfig[i] = pSensorConfigFingers[i - 6];
199 LocaliseHand(pNewCamImageLeft, pNewCamImageRight, pSensorConfig, pEstimatedConfig, dConfidenceRating);
211 handPose(0, 3) = m_pFinalConf[0];
212 handPose(1, 3) = m_pFinalConf[1];
213 handPose(2, 3) = m_pFinalConf[2];
216 Math3d::SetRotationMat(orientation, m_pFinalConf[3], m_pFinalConf[4], m_pFinalConf[5]);
218 configMutex.unlock();
220 handPose(0, 0) = orientation.r1;
221 handPose(0, 1) = orientation.r2;
222 handPose(0, 2) = orientation.r3;
223 handPose(1, 0) = orientation.r4;
224 handPose(1, 1) = orientation.r5;
225 handPose(1, 2) = orientation.r6;
226 handPose(2, 0) = orientation.r7;
227 handPose(2, 1) = orientation.r8;
228 handPose(2, 2) = orientation.r9;
244 configMutex.unlock();
246 std::vector<Vec3d>
ret;
249 Vec3d vAverage = {0, 0, 0};
258 ret.push_back(vAverage);
271 ret[i] = m_pFinalConf[i];
273 configMutex.unlock();
282 Vec3d vRotationAngles;
284 m_pFinalConf[0] = vPosition.x;
285 m_pFinalConf[1] = vPosition.y;
286 m_pFinalConf[2] = vPosition.z;
287 m_pFinalConf[3] = vRotationAngles.x;
288 m_pFinalConf[4] = vRotationAngles.y;
289 m_pFinalConf[5] = vRotationAngles.z;
292 m_pFinalConf[i] = pConfigFingers[i - 6];
294 configMutex.unlock();
305 ret[i] = m_pSensorConf[i];
307 configMutex.unlock();
316 Vec3d vRotationAngles;
318 m_pSensorConf[0] = vPosition.x;
319 m_pSensorConf[1] = vPosition.y;
320 m_pSensorConf[2] = vPosition.z;
321 m_pSensorConf[3] = vRotationAngles.x;
322 m_pSensorConf[4] = vRotationAngles.y;
323 m_pSensorConf[5] = vRotationAngles.z;
326 m_pSensorConf[i] = pConfigFingers[i - 6];
328 configMutex.unlock();
333 void CHandLocalisation::LocaliseHand(
const CByteImage* pNewCamImageLeft,
const CByteImage* pNewCamImageRight,
const double* pSensorConfig,
double* pEstimatedConfig,
double& dConfidenceRating)
335 Mat3d mTemp1, mTemp2, mTemp3, mTemp4;
355 m_pSensorConf[i] = pSensorConfig[i];
357 configMutex.unlock();
365 #pragma omp parallel sections
369 ImageProcessor::CalculateHSVImage(pNewCamImageLeft, m_pHSVImageLeft);
370 ImageProcessor::FilterHSV(m_pHSVImageLeft,
m_pColorFilteredImageLeft, default_fingertip_hue, default_fingertip_hue_tolerance,
371 default_fingertip_sat_min, default_fingertip_sat_max, default_fingertip_val_min,
372 default_fingertip_val_max);
379 ImageProcessor::CalculateHSVImage(pNewCamImageRight, m_pHSVImageRight);
380 ImageProcessor::FilterHSV(m_pHSVImageRight,
m_pColorFilteredImageRight, default_fingertip_hue, default_fingertip_hue_tolerance,
381 default_fingertip_sat_min, default_fingertip_sat_max, default_fingertip_val_min,
382 default_fingertip_val_max);
389 ImageProcessor::ConvertImage(pNewCamImageLeft, m_pTempGrayImage3);
390 ImageProcessor::CalculateGradientImageSobel(m_pTempGrayImage3, m_pTempGrayImage4);
391 for (
int i = 0; i < m_pTempGrayImage4->width * m_pTempGrayImage4->height; i++)
393 m_pTempGrayImage4->pixels[i] = 15 *
sqrt(m_pTempGrayImage4->pixels[i]);
396 #ifdef DSHT_USE_EDGE_DIRECTION
397 ImageProcessor::SobelX(m_pTempGrayImage3, m_pTempGrayImage4,
false);
398 ImageProcessor::GaussianSmooth3x3(m_pTempGrayImage4, m_pSobelXImageLeft);
399 ImageProcessor::SobelY(m_pTempGrayImage3, m_pTempGrayImage4,
false);
400 ImageProcessor::GaussianSmooth3x3(m_pTempGrayImage4, m_pSobelYImageLeft);
401 #endif // DSHT_USE_EDGE_DIRECTION
406 ImageProcessor::ConvertImage(pNewCamImageRight, m_pTempGrayImage5);
407 ImageProcessor::CalculateGradientImageSobel(m_pTempGrayImage5, m_pTempGrayImage6);
408 for (
int i = 0; i < m_pTempGrayImage6->width * m_pTempGrayImage6->height; i++)
410 m_pTempGrayImage6->pixels[i] = 15 *
sqrt(m_pTempGrayImage6->pixels[i]);
413 #ifdef DSHT_USE_EDGE_DIRECTION
414 ImageProcessor::SobelX(m_pTempGrayImage5, m_pTempGrayImage6,
false);
415 ImageProcessor::GaussianSmooth3x3(m_pTempGrayImage6, m_pSobelXImageRight);
416 ImageProcessor::SobelY(m_pTempGrayImage5, m_pTempGrayImage6,
false);
417 ImageProcessor::GaussianSmooth3x3(m_pTempGrayImage6, m_pSobelYImageRight);
418 #endif // DSHT_USE_EDGE_DIRECTION
429 m_pObjectFinderLeft->PrepareImages(pNewCamImageLeft);
430 m_pObjectFinderLeft->FindObjects(pNewCamImageLeft, NULL, eBlue, default_trball_hue, default_trball_hue_tolerance,
431 default_trball_sat_min, default_trball_sat_max, default_trball_val_min,
432 default_trball_val_max, 500,
false);
433 int nNumRegions = m_pObjectFinderLeft->Finalize();
440 for (
int i = 0; i < nNumRegions && i < m_nMaxTrBallRegions; i++)
442 pRegion = &(m_pObjectFinderLeft->m_objectList.at(i).region);
443 m_pdTrBallPosXLeft[i] = 0.5 * (pRegion->min_x + pRegion->max_x);
444 m_pdTrBallPosYLeft[i] = 0.5 * (pRegion->min_y + pRegion->max_y);
445 m_pdTrBallRadiusLeft[i] = (double)(((pRegion->max_x - pRegion->min_x) > (pRegion->max_y - pRegion->min_y)) ? 0.5 * (pRegion->max_x - pRegion->min_x) : 0.5 * (pRegion->max_y - pRegion->min_y));
451 m_pParticleFilter->
SetTrackingBallPositions(m_pdTrBallPosXLeft, m_pdTrBallPosYLeft, m_pdTrBallRadiusLeft, nNumRegions,
true);
459 m_pObjectFinderRight->PrepareImages(pNewCamImageRight);
460 m_pObjectFinderRight->FindObjects(pNewCamImageRight, NULL, eBlue, default_trball_hue, default_trball_hue_tolerance,
461 default_trball_sat_min, default_trball_sat_max, default_trball_val_min,
462 default_trball_val_max, 500,
false);
463 int nNumRegions = m_pObjectFinderRight->Finalize();
466 for (
int i = 0; i < nNumRegions && i < m_nMaxTrBallRegions; i++)
468 pRegion = &(m_pObjectFinderRight->m_objectList.at(i).region);
469 m_pdTrBallPosXRight[i] = 0.5 * (pRegion->min_x + pRegion->max_x);
470 m_pdTrBallPosYRight[i] = 0.5 * (pRegion->min_y + pRegion->max_y);
471 m_pdTrBallRadiusRight[i] = (double)(((pRegion->max_x - pRegion->min_x) > (pRegion->max_y - pRegion->min_y)) ? 0.5 * (pRegion->max_x - pRegion->min_x) : 0.5 * (pRegion->max_y - pRegion->min_y));
473 m_pParticleFilter->
SetTrackingBallPositions(m_pdTrBallPosXRight, m_pdTrBallPosYRight, m_pdTrBallRadiusRight, nNumRegions,
false);
492 if (std::isnan(m_pOldFinalConf[i]))
498 if (!m_bFirstRun && !bNan)
501 for (
int i = 0; i < 3; i++)
503 m_pPredictedConf[i] = m_pOldFinalConf[i] + m_pSensorConf[i] - m_pOldSensorConf[i];
509 m_pPredictedConf[i] = m_pOldFinalConf[i] + m_pSensorConf[i] - m_pOldSensorConf[i];
510 if (m_pPredictedConf[i] < 0)
512 m_pPredictedConf[i] += 2 *
M_PI;
514 else if (m_pPredictedConf[i] >= 2 *
M_PI)
516 m_pPredictedConf[i] -= 2 *
M_PI;
521 Math3d::SetRotationMat(mTemp1, m_pSensorConf[3], m_pSensorConf[4], m_pSensorConf[5]);
522 Math3d::SetRotationMat(mTemp2, m_pOldSensorConf[3], m_pOldSensorConf[4], m_pOldSensorConf[5]);
523 Math3d::Invert(mTemp2, mTemp3);
524 Math3d::MulMatMat(mTemp1, mTemp3, mTemp4);
525 Math3d::SetRotationMat(mTemp1, m_pOldFinalConf[3], m_pOldFinalConf[4], m_pOldFinalConf[5]);
526 Math3d::MulMatMat(mTemp4, mTemp1, mTemp2);
528 m_pPredictedConf[3] = vTemp1.x;
529 m_pPredictedConf[4] = vTemp1.y;
530 m_pPredictedConf[5] = vTemp1.z;
538 if ((!m_bFirstRun) && (m_nPredictionMode >= 1) && !bNan)
557 double dAnnFact = 1.0;
558 double dAnnRedFactor = 0.5;
559 if (m_nNumAnnealingRuns > 4)
561 dAnnRedFactor = pow(0.1, 1 / (m_nNumAnnealingRuns - 1));
563 for (
int i = 0; i < m_nNumAnnealingRuns; i++)
565 ARMARX_VERBOSE_S <<
"PF: Iteration " << i + 1 <<
" of " << m_nNumAnnealingRuns;
566 m_pParticleFilter->
ParticleFilter(m_pPFConf, m_dVarianceFactor * dAnnFact);
567 dAnnFact *= dAnnRedFactor;
584 if (m_nPredictionMode == 0 || bNan)
588 m_pFinalConf[i] = m_pPFConf[i];
591 else if (m_nPredictionMode == 1 || m_nPredictionMode == 2)
598 double dMovementRating = 1;
605 m_pFinalConf[i] = m_pPFConf[i];
612 else if (m_dRating < 0.05 &&
false)
616 m_pFinalConf[i] = m_pPredictedConf[i];
621 const float fWeightingFactor = 3.0;
622 double dWeight = (fWeightingFactor * m_dRating * dMovementRating / (m_dOldRating + fWeightingFactor * m_dRating * dMovementRating));
625 for (
int i = 0; i < 3; i++)
627 m_pFinalConf[i] = dWeight * m_pPFConf[i] + (1 - dWeight) * m_pPredictedConf[i];
631 Math3d::SetRotationMat(mTemp1, m_pPredictedConf[3], m_pPredictedConf[4], m_pPredictedConf[5]);
632 Math3d::SetRotationMat(mTemp2, m_pPFConf[3], m_pPFConf[4], m_pPFConf[5]);
633 Math3d::Invert(mTemp1, mTemp3);
634 Math3d::MulMatMat(mTemp2, mTemp3, mTemp4);
635 Math3d::GetAxisAndAngle(mTemp4, vTemp1, fTemp1);
637 Math3d::SetRotationMatAxis(mTemp3, vTemp1, fTemp1);
638 Math3d::MulMatMat(mTemp3, mTemp1, mTemp2);
640 m_pFinalConf[3] = vTemp1.x;
641 m_pFinalConf[4] = vTemp1.y;
642 m_pFinalConf[5] = vTemp1.z;
647 m_pFinalConf[i] = dWeight * m_pPFConf[i] + (1 - dWeight) * m_pPredictedConf[i];
653 if (m_nPredictionMode == 2)
660 m_pFinalConf[i] = 0.7 * pTempConf[i] + 0.3 * m_pFinalConf[i];
677 pEstimatedConfig[i] = m_pFinalConf[i];
678 m_pOldFinalConf[i] = m_pFinalConf[i];
679 m_pOldSensorConf[i] = m_pSensorConf[i];
680 m_pOldPFConf[i] = m_pPFConf[i];
682 m_dOldRating = m_dRating;
684 configMutex.unlock();