J'ai une image convertie en CvMat
Matrice dire CVMat source
. Une fois que j'obtiens une région d'intérêt de source
je veux que le reste de l'algorithme soit appliqué à cette région d'intérêt uniquement. Pour cela, je pense que je devrai en quelque sorte recadrer la source
ce que je suis incapable de faire. Existe-t-il une méthode ou une fonction qui pourrait recadrer une CvMat
et renvoyer une autre matrice CvMat
recadrée ? Merci.
Réponses
Trop de publicités?OpenCV a des fonctions de région d'intérêt que vous pouvez trouver utiles. Si vous utilisez le cv::Mat
vous pouvez utiliser quelque chose comme ce qui suit.
// You mention that you start with a CVMat* imagesource
CVMat * imagesource;
// Transform it into the C++ cv::Mat format
cv::Mat image(imagesource);
// Setup a rectangle to define your region of interest
cv::Rect myROI(10, 10, 100, 100);
// Crop the full image to that image contained by the rectangle myROI
// Note that this doesn't copy the data
cv::Mat croppedImage = image(myROI);
Pour obtenir de meilleurs résultats et une meilleure robustesse contre différents types de matrices, vous pouvez faire ceci en plus de la première réponse, qui copie les données :
cv::Mat source = getYourSource();
// Setup a rectangle to define your region of interest
cv::Rect myROI(10, 10, 100, 100);
// Crop the full image to that image contained by the rectangle myROI
// Note that this doesn't copy the data
cv::Mat croppedRef(source, myROI);
cv::Mat cropped;
// Copy the data into new matrix
croppedRef.copyTo(cropped);
Pour créer une copie du recadrage souhaité, nous pouvons procéder comme suit,
// Read img
cv::Mat img = cv::imread("imgFileName");
cv::Mat croppedImg;
// This line picks out the rectangle from the image
// and copies to a new Mat
img(cv::Rect(xMin,yMin,xMax-xMin,yMax-yMin)).copyTo(croppedImg);
// Display diff
cv::imshow( "Original Image", img );
cv::imshow( "Cropped Image", croppedImg);
cv::waitKey();
Je comprends que cette question a reçu une réponse, mais peut-être que cela pourrait être utile à quelqu'un...
Si vous souhaitez copier les données dans un objet cv::Mat séparé, vous pouvez utiliser une fonction similaire à celle-ci :
void ExtractROI(Mat& inImage, Mat& outImage, Rect roi){
/* Create the image */
outImage = Mat(roi.height, roi.width, inImage.type(), Scalar(0));
/* Populate the image */
for (int i = roi.y; i < (roi.y+roi.height); i++){
uchar* inP = inImage.ptr<uchar>(i);
uchar* outP = outImage.ptr<uchar>(i-roi.y);
for (int j = roi.x; j < (roi.x+roi.width); j++){
outP[j-roi.x] = inP[j];
}
}
}
Il serait important de noter que cela ne fonctionnerait correctement que sur des images monocanal .