Problem in image segmentation using watershed on android

耗尽温柔 提交于 2020-06-17 14:18:26

问题


I am developing an application that segments images of wounds using the watershed algorithm. For this, the user draws a line in the internal area of ​​the wound (region of interest) and another drawing in the background. With that, I pass the coordinates of this drawing to the watershed to perform the segmentation. I used this code in python to guide me through this step. However, in addition to not performing the correct segmentation, the black / white image is being saved in a different orientation than the original image. In the final image, the segmented image is not appearing, but the original image. I would like someone to help me correct these errors.

Code:

override fun onActivityResult(requestCode: Int, resultCode: Int, resultData: Intent?) {
    super.onActivityResult(requestCode, resultCode, resultData)
    if (requestCode == PICK_IMAGE_INTENT && resultCode == Activity.RESULT_OK && resultData != null && resultData.data != null) {
        tryOpenUri(resultData.data!!, resultData)
        val selectedImage = if (resultData.data != null) {
            resultData.data
        } else {
            resultData.clipData?.getItemAt(0)?.uri
        }
        imageUpload = true
        val filePathColumn = arrayOf(MediaStore.Images.Media.DATA)
        val cursor = contentResolver.query(selectedImage!!, filePathColumn, null, null, null)!!
        cursor.moveToFirst()
        currentPhotoPath = cursor.moveToFirst()
            .let { cursor.getString(cursor.getColumnIndex(filePathColumn[0])) }
            .also { cursor.close() }
        cursor.close()

    } else if (requestCode == SAVE_IMAGE_INTENT && resultCode == Activity.RESULT_OK && resultData != null && resultData.data != null) {
        val outputStream = contentResolver.openOutputStream(resultData.data!!)
        saveToOutputStream(outputStream, defaultPath.getCompressionFormat(), false)
        savedPathsHash = my_canvas.getDrawingHashCode()
        imageUpload = true
    }
}

private fun regionBackground() {

    progressDialog = ProgressDialog(this, R.style.MyDialogTheme)
    progressDialog.setTitle("Wait..")
    progressDialog.setMessage("save the draw...")
    progressDialog.show()
    progressDialog.setCancelable(false)
    //Load the image
    srcOriginal = Imgcodecs.imread(currentPhotoPath)
    //Create a blank image of zeros (same dimension as img)
    //It should be grayscale (1 color channel)
    markers = Mat.zeros(srcOriginal.rows(), srcOriginal.cols(), CvType.CV_32S)
    //This step is manual. The goal is to find the points
    //which create the result we want. I suggest using a
    //tool to get the pixel coordinates.
    //Dictate the background and set the markers to 1
    for (value in 0..my_canvas.pointsToDrawY.size - 1) {
        markers.put(
            my_canvas.pointsToDrawX[value].toInt(),
            my_canvas.pointsToDrawY[value].toInt(),
            1.0
        )
    }
    my_canvas.pointsToDrawXStepTwo.clear()
    my_canvas.pointsToDrawYStepTwo.clear()

   //Log.i("teste", my_canvas.pointsToDrawXStepTwo.toString()+"x"+my_canvas.pointsToDrawYStepTwo)
    Handler().postDelayed({
        progressDialog.dismiss()
    }, 1000)
}

private fun regionOfInterest() {
    //Log.i("teste", my_canvas.pointsToDrawXStepTwo.toString()+"x"+my_canvas.pointsToDrawYStepTwo)
    progressDialog = ProgressDialog(this, R.style.MyDialogTheme)
    progressDialog.setTitle("Wait..")
    progressDialog.setMessage("save the draw...")
    progressDialog.show()
    progressDialog.setCancelable(false)
    //Dictate the area of interest
    //I used different values for each part of the car (for visibility)
    for (value in 0..my_canvas.pointsToDrawYStepTwo.size - 1) {
        markers.put(
            my_canvas.pointsToDrawXStepTwo[value].toInt(),
            my_canvas.pointsToDrawYStepTwo[value].toInt(),
            255.0
        )
    }
    Handler().postDelayed({
        watershedSegmentation()
    }, 1000)

}

private fun watershedSegmentation() {
    //Now we have set the markers, we use the watershed
    //algorithm to generate a marked image
    watershed(srcOriginal, markers)
    //Plot this one. If it does what we want, proceed;
    //otherwise edit your markers and repeat
    val mPath1 = Environment.getExternalStorageDirectory().toString() + "/watershed.png"
    Imgcodecs.imwrite(mPath1,markers)
    //Make the background black, and what we want to keep white
    for (x in 0 until srcOriginal.rows()-1) {
        for (y in 0 until srcOriginal.cols()-1) {
            if(markers.get(x,y).get(0).equals(1.0)){
                markers.put(
                    x,
                    y,
                    0.0
                )
            }
            if((markers[x, y].get(0) == 255.0)){
                markers.put(
                    x,
                    y,
                    255.0
                )
            }
        }
    }
    //Use a kernel to dilate the image, to not lose any detail on the outline
    //I used a kernel of 3x3 pixels
    val marker_tempo = Mat()
    val dilatation = Mat()
    markers.convertTo(marker_tempo, CvType.CV_8U)
    val kernel = Mat(1, 1, CvType.CV_8U)
    //Plot again to check whether the dilation is according to our needs
    //If not, repeat by using a smaller/bigger kernel, or more/less iterations
    Imgproc.dilate(marker_tempo, dilatation, kernel)
    val mPath2 = Environment.getExternalStorageDirectory().toString() + "/dilatation.png"
    Imgcodecs.imwrite(mPath2,dilatation)
    //Now apply the mask we created on the initial image
    Core.bitwise_and(srcOriginal, srcOriginal, dilatation)
    //Plot the final result
    val mPath = Environment.getExternalStorageDirectory().toString() + "/final.png"
    Imgcodecs.imwrite(mPath,dilatation)


    Handler().postDelayed({
        progressDialog.dismiss()
        Toast.makeText(this, "Image segmented!", Toast.LENGTH_SHORT).show()
    }, 1000)


}

original image

Draw regions

Create a blank image of zeros (same dimension as img original) - why is it getting rotated? and how to improve this segmentation?

output image dilated:

output image final:

what's missing to be able to target this image correctly?

来源:https://stackoverflow.com/questions/62159692/problem-in-image-segmentation-using-watershed-on-android

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!