Home > Software design >  YCbCr() not giving same result after inverse, using Kotlin Android
YCbCr() not giving same result after inverse, using Kotlin Android

Time:11-05

Code for converting RGB bitmap to YCbCr bitmap:

private fun rgbToYcbcr(bitmap: Bitmap): Bitmap {
    val width: Int = bitmap.width
    val height: Int = bitmap.height
    var pixel: Int
    var red: Int
    var green: Int
    var blue: Int
    var yC: Int
    var cb: Int
    var cr: Int
    val outputBM = Bitmap.createBitmap(width, height, bitmap.config)
    for (x in 0 until width) {
        for (y in 0 until height) {
            pixel = bitmap.getPixel(x, y)
            red = Color.red(pixel)
            green = Color.green(pixel)
            blue = Color.blue(pixel)
            yC = (0.299 * red   0.587 * green   0.114 * blue).toInt()
            cb = (128 - 0.169 * red - 0.331 * green   0.500 * blue).toInt()
            cr = (128   0.500 * red - 0.419 * green - 0.081 * blue).toInt()
            val p = yC shl 24 or (cb shl 16) or (cr shl 8)
            outputBM.setPixel(x, y, p)
        }
    }
    return ycbcrToRgb(outputBM)
}

Code for converting YCbCr bitmap back to RGB bitmap:

private fun ycbcrToRgb(ycbcrBitmap: Bitmap): Bitmap {
    val width = ycbcrBitmap.width
    val height = ycbcrBitmap.height
    val outputBM = Bitmap.createBitmap(width, height, ycbcrBitmap.config)
    for (x in 0 until width) {
        for (y in 0 until height) {
            val pixel = ycbcrBitmap.getPixel(x, y)
            val yC = Color.red(pixel)
            val cb = Color.green(pixel)
            val cr = Color.blue(pixel)
            val red = (yC   1.402 * (cr - 128)).toInt()
            val green = (yC - 0.34414 * (cb - 128) - 0.71414 * (cr - 128)).toInt()
            val blue = (yC   1.772 * (cb - 128)).toInt()
            val rgbPixel = Color.rgb(
                red.coerceIn(0, 255),
                green.coerceIn(0, 255),
                blue.coerceIn(0, 255)
            )
            outputBM.setPixel(x, y, rgbPixel)
        }
    }
    return outputBM
}

I am not getting desired result. I am converting RGB image to YCbCr image. But after converting it back from YCbCr to RGB, I don't get same image what I provide.

CodePudding user response:

The issue you're facing could be related to the conversion between RGB and YCbCr color spaces. The formulas you are using for conversion appear to be based on the typical YCbCr conversion formulas.

Update your rgbToYcbcr() as shown below:

private fun rgbToYcbcr(bitmap: Bitmap): Bitmap {
    val width: Int = bitmap.width
    val height: Int = bitmap.height
    var pixel: Int
    var red: Int
    var green: Int
    var blue: Int
    var yC: Int
    var cb: Int
    var cr: Int
    val outputBM = Bitmap.createBitmap(width, height, bitmap.config)
    for (x in 0 until width) {
        for (y in 0 until height) {
            pixel = bitmap.getPixel(x, y)
            red = Color.red(pixel)
            green = Color.green(pixel)
            blue = Color.blue(pixel)
            yC = (0.299 * red   0.587 * green   0.114 * blue).toInt()
            cb = (128 - 0.169 * red - 0.331 * green   0.500 * blue).toInt()
            cr = (128   0.500 * red - 0.419 * green - 0.081 * blue).toInt()
            yC = yC.coerceIn(16, 235)
            cb = cb.coerceIn(16, 240)
            cr = cr.coerceIn(16, 240)
            val p = Color.rgb(yC, cb, cr)
            outputBM.setPixel(x, y, p)
        }
    }
    return ycbcrToRgb(outputBM)
}
  • Related