A app has been created using Kotlin which will ask the user to select an image from the gallery. Then the user has two button compress image and decompress image.
Now the problem is that when we are compressing the image then the image size dropped to 85% but when trying to decompress that image then it not even able to attain up to 70% of original image size. For compressing and decompressing I am using BitMapFactory. Is there anyway to decompress the image to regain the image quality >= 80.
The MainActivity.kt code:
import android.content.Intent
import android.graphics.Bitmap
import android.graphics.BitmapFactory
import android.Uri
import android.os.Bundle
import android.provider.MediaStore
import android.widget.Button
import android.widget.ImageView
import android.widget.Toast
import androidx.activity.result.contract.ActivityResultContracts
import androidx.appcompat.app.AppCompatActivity
import java.io.ByteArrayOutputStream
import java.io.IOException
class MainActivity : AppCompatActivity() {
private lateinit var displayImage: ImageView //image selected
private lateinit var compressedImageView: ImageView //image after compression or decompression
private lateinit var selectImage: Button // button for selecting image from gallery
private lateinit var compressButton: Button // button to start compression
private lateinit var decompressButton: Button // Button to start decompression
private var imageUri: Uri? = null
private var compressedImageBytes: ByteArray? = null
private var decompressedImageBytes: ByteArray? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
displayImage = findViewById(R.id.imageView)
compressedImageView = findViewById(R.id.imageView2)
selectImage = findViewById(R.id.upload)
compressButton = findViewById(R.id.uploadWithCompress)
decompressButton = findViewById(R.id.decompressImage)
selectImage.setOnClickListener {
val intent = Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI)
pickImageLauncher.launch(intent)
}
compressButton.setOnClickListener {
imageUri?.let { compressImage(it) }
}
decompressButton.setOnClickListener {
compressedImageBytes?.let { decompressImage(it) }
}
}
private val pickImageLauncher = registerForActivityResult(ActivityResultContracts.StartActivityForResult()) { result ->
if (result.resultCode == RESULT_OK) {
result.data?.data?.let {
imageUri = it
displayImage.setImageURI(it)
}
}
}
private fun compressImage(uri: Uri) {
try {
val bmp = MediaStore.Images.Media.getBitmap(contentResolver, uri)
val baos = ByteArrayOutputStream()
bmppress(Bitmap.CompressFormat.JPEG, 25, baos)
compressedImageBytes = baos.toByteArray()
val compressedBitmap = BitmapFactory.decodeByteArray(compressedImageBytes, 0, compressedImageBytes!!.size)
compressedImageView.setImageBitmap(compressedBitmap)
val compressedSizeKB = compressedImageBytes!!.size / 1024
Toast.makeText(this, "Compressed Image Size: $compressedSizeKB KB", Toast.LENGTH_SHORT).show()
} catch (e: IOException) {
e.printStackTrace()
}
}
private fun decompressImage(compressedBytes: ByteArray) {
val decompressedBitmap = BitmapFactory.decodeByteArray(compressedBytes, 0, compressedBytes.size)
compressedImageView.setImageBitmap(decompressedBitmap)
val decompressedSizeKB = compressedImageBytes!!.size / 1024
Toast.makeText(this, "Image Decompressed to Original Quality and its size is: $decompressedSizeKB KB", Toast.LENGTH_SHORT).show()
}
}
I now that it is near to impossible to regain the original quality of compressed image to its original form, but then also if it is possible using any external tool, then please share it here.