Home > other >  How can skinDetected area in an image be converted to 0, 1 matrix of type CV_8UC4 in openCV JS?
How can skinDetected area in an image be converted to 0, 1 matrix of type CV_8UC4 in openCV JS?

Time:10-07

I need a 0-1 matrix where 1 denotes the presence of skin and 0 denotes other part of the image. I am using openCV Js for image processing but since "skinArea" is of type CV_8UC1, it can't be divided with "mat255" of type CV_8UC4. I require the "Mat0_1" matrix of type CV_8UC4 to do further computations.

let minRange = new cv.Mat(img.rows, img.cols, img.type(), [72,22, 37, 0]);
let maxRange = new cv.Mat(img.rows, img.cols, img.type(), [173, 235, 127, 255]);
cv.inRange(img, minRange, maxRange, skinArea);
let mat255 = new cv.Mat(img.rows, img.cols, cv.CV_8UC4,new cv.Scalar(255,255,255,0))
cv.divide(skinArea,mat255,Mat0_1);

CodePudding user response:

We may convert from CV_8UC1 to cv.CV_8UC4 by executing cvtColor with cv.COLOR_GRAY2BGRA argument:

cv.cvtColor(skinArea, skinAreaBinaryBgra, cv.COLOR_GRAY2BGRA);

The first three channels of every 4 applies BGR (for grayscale blue=green=red).
The 4'th channel is alpha (transparency) channel - the conversion sets all alpha elements to 255 (fully opaque).

Instead of dividing by 255, we may use cv.min(skinArea, ones, skinAreaBinary); (only because division operation is considered inefficient).


Code sample:

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello OpenCV.js</title>
</head>

<body>
<p id="status">OpenCV.js is loading...</p>
<div>
  <div >
    <img id="imageSrc" alt="No Image" />
    <div >imageSrc <input type="file" id="fileInput" name="file" /></div>
  </div>
  <div >
    <canvas id="canvasOutput" ></canvas>
    <div >canvasOutput</div>
  </div>
</div>

<script async src="opencv.js" type="text/javascript"></script>


<script type="text/javascript">
let imgElement = document.getElementById('imageSrc');
let inputElement = document.getElementById('fileInput');
inputElement.addEventListener('change', (e) => {
  imgElement.src = URL.createObjectURL(e.target.files[0]);
}, false);

//Read image and execute the OpenCV code sample.
imgElement.onload = function () {
  let img = cv.imread(imgElement);
  let skinArea = new cv.Mat()
  let skinAreaBinary = new cv.Mat()
  let skinAreaBinaryBgra = new cv.Mat()
  let skinAreaBinaryBgraShow = new cv.Mat()

  let minRange = new cv.Mat(img.rows, img.cols, img.type(), [72,22, 37, 0]);
  let maxRange = new cv.Mat(img.rows, img.cols, img.type(), [173, 235, 127, 255]);
  cv.inRange(img, minRange, maxRange, skinArea);

  //let mat255 = new cv.Mat(img.rows, img.cols, cv.CV_8UC4,new cv.Scalar(255,255,255,0))
  //cv.divide(skinArea,mat255,Mat0_1);
  let ones = new cv.Mat(img.rows, img.cols, cv.CV_8UC1, new cv.Scalar(1)); //Matrix of ones
  cv.min(skinArea, ones, skinAreaBinary); //min(val, 1) is more efficient than dividing by 255.

  cv.cvtColor(skinArea, skinAreaBinaryBgra, cv.COLOR_GRAY2BGRA); //Convert to 4 channels (BGRA pixel format).

  skinAreaBinaryBgra.convertTo(skinAreaBinaryBgraShow, cv.CV_8U, 255.0); //Scale by 255 before displaying (for testing).
  cv.imshow('canvasOutput', skinAreaBinaryBgraShow); //Show result for testing
};


//check openCV
var Module = {
  // https://emscripten.org/docs/api_reference/module.html#Module.onRuntimeInitialized
  onRuntimeInitialized() {
    document.getElementById('status').innerHTML = 'OpenCV.js is ready.';
  }
};
</script>

</body>
</html>
  • Related