У меня проблема с наложением дефектов выпуклости на раму. Чтобы вычислить их, я изменил исходный код на С ++, и вот что я заархивировал:
mConvexityDefectsMatOfInt4 = new MatOfInt4();
if(contours.size() > 0 && convexHullMatOfInt.rows() > 0)
Imgproc.convexityDefects(contours.get(0), convexHullMatOfInt, mConvexityDefectsMatOfInt4);
Однако метод Imgproc.drawContours (…) требует, чтобы выпуклым элементам, переданным ему в качестве параметров, был ArrayList. Я не знаю, как я могу сделать преобразование. У меня была похожая проблема с выпуклыми корпусами, но я обнаружил обход:
convexHullMatOfInt = new MatOfInt();
convexHullPointArrayList = new ArrayList<Point>();
convexHullMatOfPoint = new MatOfPoint();
convexHullMatOfPointArrayList = new ArrayList<MatOfPoint>();
//Calculate convex hulls
if(contours.size() > 0)
{
Imgproc.convexHull( contours.get(0), convexHullMatOfInt, false );
for(int j=0; j < convexHullMatOfInt.toList().size(); j++)
convexHullPointArrayList.add(contours.get(0).toList().get(convexHullMatOfInt.toList().get(j)));
convexHullMatOfPoint.fromList(convexHullPointArrayList);
convexHullMatOfPointArrayList.add(convexHullMatOfPoint);
}
Подобное решение для дефектов выпуклости не работает. У кого-нибудь есть идеи как решить проблему?
Как преобразовать MatOfInt4 () в ArrayList (), чтобы иметь возможность рисовать дефекты выпуклости?
(Я сам так много боролся с convexityDefect
что я хотел убить любого, кто написал интерфейс Java для OpenCV!)
Теперь ответ:
Как указано в документы, MatOfInt4
в основном 4-элементный целочисленный массив, содержащий следующую информацию:
start_index
end_index
farthest_pt_index
fixpt_depth
Вы можете использовать следующие для преобразования mConvexityDefectsMatOfInt4
в список целых чисел:
List<Integer> cdList = mConvexityDefectsMatOfInt4.toList();
Теперь каждые 4 последовательных элемента в cdList
содержит информацию, указанную выше:
cdList 0 : 23
cdList 1 : 30
cdList 2 : 26
cdList 3 : 18101
-----------------
cdList 4 : 30
cdList 5 : 44
cdList 6 : 33
cdList 7 : 43738
Так, например, если вы хотите нарисовать только самую дальнюю точку каждой вогнутости, вы можете просто использовать третий индекс каждого из 4 элементов. В этом случае: 26, 33, …
Надеюсь, поможет.
Вот пример:
for (int i = 0; i < contours.size(); i++) {
convDef.add(new MatOfInt4());
Imgproc.convexityDefects(contours.get(i), hull.get(i),
convDef.get(i));
cdList = convDef.get(i).toList();
Point data[] = contours.get(i).toArray();
for (int j = 0; j < cdList.size(); j = j+4) {
Point start = data[cdList.get(j)];
Point end = data[cdList.get(j+1)];
Point defect = data[cdList.get(j+2)];
//Point depth = data[cdList.get(j+3)];
Imgproc.circle(mat, start, 5, new Scalar(0, 255, 0), 2);
Imgproc.circle(mat, end, 5, new Scalar(0, 255, 0), 2);
Imgproc.circle(mat, defect, 5, new Scalar(0, 255, 0), 2);
}
}