Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/three.js/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 尝试从深度图像提取手轮廓时出现无效矩阵错误_C++_Opencv_Openni - Fatal编程技术网

C++ 尝试从深度图像提取手轮廓时出现无效矩阵错误

C++ 尝试从深度图像提取手轮廓时出现无效矩阵错误,c++,opencv,openni,C++,Opencv,Openni,我正在使用OpenCV和OpenNI从Xtion传感器生成的深度图像中提取一只手,然后提取单个手指。当为hands generator执行聚焦手势时,hasHand bool设置为true,并运行下面的代码。手[]是一个浮动数组,其中包含被跟踪手的x、y和z坐标 if(hasHand) { unsigned char shade = 255 - (unsigned char)(hand[2] * 128.0f); Scalar color(0, shad

我正在使用OpenCV和OpenNI从Xtion传感器生成的深度图像中提取一只手,然后提取单个手指。当为hands generator执行聚焦手势时,hasHand bool设置为true,并运行下面的代码。手[]是一个浮动数组,其中包含被跟踪手的x、y和z坐标

if(hasHand)
    {
        unsigned char shade = 255 - (unsigned char)(hand[2] *  128.0f);
        Scalar color(0, shade, 0);

        vector<Point> handContour;
        getHandContour(depthMat, hand, handContour);
        bool grasp = convexity(handContour) > grabConvexity; //PROBLEM
        int thickness = grasp ? CV_FILLED : 3;
        circle(depthMatBgr, Point(hand[0], hand[1]), 10, color, thickness);

        vector<Point> fingerTips;
        detectFingerTips(handContour, fingerTips, &depthMatBgr);
    }
我已经被这个问题困扰了一段时间,我不知道为什么我会遇到这个问题。getHandContour的代码为:

bool getHandContour(const Mat &depthMat, const float *v, vector<Point> &handContour) 
{
const int maxHandRadius = 128; // in px
const short handDepthRange = 200; // in mm
const double epsilon = 17.5; // approximation accuracy (maximum distance between    the original hand contour and its approximation)

depth = v[2] * 1000.0f; // hand depth
nearClip = depth - 100; // near clipping plane
farClip = depth + 100; // far clipping plane

static Mat mask(frameSize, CV_8UC1);
mask.setTo(0);

// extract hand region  
circle(mask, Point(v[0], v[1]), maxHandRadius, 255, CV_FILLED);
mask = mask & depthMat > nearClip & depthMat < farClip;

// DEBUG(show mask)
imshow("mask1", mask);

// assume largest contour in hand region to be the hand contour
vector<vector<Point> > contours;
findContours(mask, contours, CV_RETR_LIST, CV_CHAIN_APPROX_SIMPLE);
int n = contours.size();
int maxI = -1;
int maxSize = -1;
for (int i=0; i<n; i++) {
    int size  = contours[i].size();
    if (size > maxSize) {
        maxSize = size;
        maxI = i;
    }
}

bool handContourFound = (maxI >= 0);

if (handContourFound) {
    approxPolyDP( Mat(contours[maxI]), handContour, epsilon, true );
}

return maxI >= 0;
}
bool getHandContour(常数矩阵和深度、常数浮点*v、向量和handContour)
{
常量int maxHandRadius=128;//以px为单位
const short HANDDEPTRANGE=200;//单位:mm
const double epsilon=17.5;//近似精度(原始手轮廓与其近似值之间的最大距离)
深度=v[2]*1000.0f;//手部深度
nearClip=depth-100;//近剪裁平面
远剪裁=深度+100;//远剪裁平面
静态垫掩模(框架尺寸,CV_8UC1);
掩码设置为(0);
//提取手部区域
圆(遮罩,点(v[0],v[1]),最大半径,255,CV_填充);
遮罩=遮罩和深度>近剪辑和深度<远剪辑;
//调试(显示掩码)
imshow(“mask1”,mask);
//假设手部区域中的最大轮廓为手部轮廓
矢量等值线;
findContours(遮罩、轮廓、CV_RETR_列表、CV_链近似_简单);
int n=等高线.size();
int maxI=-1;
int maxSize=-1;
对于(int i=0;i maxSize){
最大尺寸=尺寸;
maxI=i;
}
}
布尔值=(最大值>=0);
如果(找到){
approxPolyDP(Mat(等高线[maxI]),手等高线,ε,真);
}
返回最大值>=0;
}
我不确定这些信息是否足够让人们帮助我(这对很多人来说都是新的),但如果你能朝着正确的方向努力,我将不胜感激

编辑:对不起,我忘了在这个问题中包含凸性()代码:

double convexity(const vector<Point> &contour) {
Mat contourMat(contour);

vector<int> hull;
convexHull(contourMat, hull);

int n = hull.size();
vector<Point> hullContour;

for (int i=0; i<n; i++) {
    hullContour.push_back(contour[hull[i]]);
}

Mat hullContourMat(hullContour);

return (contourArea(contourMat) / contourArea(hullContourMat));
}
双凸性(常量向量和等高线){
垫轮廓垫(轮廓);
向量壳;
convexHull(轮廓垫、船体);
int n=hull.size();
向量向量向量;

对于(int i=0;i我相信approxPolyDP只需要一个计数,当您试图传递整个列表时,

OpenCV
的调用不会直接在该行上发生,对吗?(
凸性
不是
OpenCV
函数,对吧?)这意味着在
凸性
中的某个地方,您正在调用
OpenCV
并传入一个无效的矩阵。请注意,对
OpenCV
的调用可能位于与您想象的不同的行上(例如在
gethandcourto
中)如果您在调试方面没有足够的经验。您需要做的第一件事是找到您实际输入
OpenCV
的位置。然后尝试在独立程序中重现错误。您可以显示凸性()实现。似乎它需要类似Mat类型(即OpenCV类型)的东西。我现在已经添加了凸面()实现,很抱歉,它一开始就不存在。我不确定这在您的情况下是否重要,但有时(奇怪的是,并不总是)会使用限定名称,如cv::convexHull(handContourMat,hull);。您可以在此处进行比较-
double convexity(const vector<Point> &contour) {
Mat contourMat(contour);

vector<int> hull;
convexHull(contourMat, hull);

int n = hull.size();
vector<Point> hullContour;

for (int i=0; i<n; i++) {
    hullContour.push_back(contour[hull[i]]);
}

Mat hullContourMat(hullContour);

return (contourArea(contourMat) / contourArea(hullContourMat));
}