-
-
Save ayetolusamuel/cfe765433058a6d0de877b76d0065434 to your computer and use it in GitHub Desktop.
//runtime permission check for location | |
fun checkPermission(): Boolean{ | |
return ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED | |
} | |
//request permission | |
fun requestPermission(){ | |
ActivityCompat.requestPermissions(this, | |
arrayOf(Manifest.permission.ACCESS_FINE_LOCATION), | |
locationPermissionCode) | |
} |
//custom toast
fun Activity.customToast(message: String = getString(R.string.invalid_login_details)) {
val inflater = layoutInflater
val layout = inflater.inflate(R.layout.custom_toast, custom_toast_container) as ViewGroup
val displayMessage = layout.findViewById(R.id.message)
val toast = Toast(applicationContext)
displayMessage.text = message
toast.setGravity(Gravity.BOTTOM, 0, 64)
toast.duration = Toast.LENGTH_SHORT
toast.view = layout
toast.show()
}
//validate email
fun isValidEmail(target: CharSequence?) = Patterns.EMAIL_ADDRESS.matcher(target!!).matches()
//hidekeyboard
fun Activity.hideKeyboard() {
try {
val inputMethodManager: InputMethodManager? =
getSystemService(Activity.INPUT_METHOD_SERVICE) as InputMethodManager?
inputMethodManager?.hideSoftInputFromWindow(currentFocus!!.windowToken, 0)
} catch (exception: Exception) {
exception.printStackTrace()
}
}
public static void hideKeyboard(Activity activity) {
InputMethodManager imm = (InputMethodManager) activity.getSystemService(Activity.INPUT_METHOD_SERVICE);
//Find the currently focused view, so we can grab the correct window token from it.
View view = activity.getCurrentFocus();
//If no view currently has focus, create a new one, just so we can grab a window token from it
if (view == null) {
view = new View(activity);
}
imm.hideSoftInputFromWindow(view.getWindowToken(), 0);
}
public static void hideKeyboardFrom(Context context, View view) {
InputMethodManager imm = (InputMethodManager) context.getSystemService(Activity.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(view.getWindowToken(), 0);
}
// Check if no view has focus:
val view = this.currentFocus
view?.let { v ->
val imm = getSystemService(Context.INPUT_METHOD_SERVICE) as? InputMethodManager
imm?.hideSoftInputFromWindow(v.windowToken, 0)
}
save/retrieve encrypt & decrypt
fun Context.saveDataToBeEncrypted(map: HashMap<String, ByteArray>) {
val sharedPreferences = getDefaultSharedPreferences(this)
val editor = sharedPreferences.edit()
val gSon = Gson()
val valueString = gSon.toJson(map)
editor.putString(ENCRYPTED_PREFERENCE_VALUE, valueString).apply()
}
fun Context.getDataEncrypted(): HashMap<String, ByteArray> {
val sharedPreferences = getDefaultSharedPreferences(this)
val valueString = sharedPreferences.getString(ENCRYPTED_PREFERENCE_VALUE, "")
return Gson().fromJson(
valueString,
object : TypeToken<HashMap<String?, ByteArray?>?>() {}.type
)
}
//bitmap to byteArray
fun convertBitmapToByteArray(bitmap: Bitmap): ByteArray {
val stream = ByteArrayOutputStream()
bitmap.compress(Bitmap.CompressFormat.PNG, 100, stream)
val byteArray: ByteArray = stream.toByteArray()
bitmap.recycle()
return byteArray
}
//encrypt and decrypt
fun encrypt(encryptedValue: ByteArray): HashMap<String, ByteArray> {
val map = HashMap<String, ByteArray>()
val random = SecureRandom()
val salt = ByteArray(256)
random.nextBytes(salt)
val passwordChar = ENCRYPTED_VALUE.toCharArray()
val pbKeySpec = PBEKeySpec(passwordChar, salt, 1324, 256)
val secretKeyFactory = SecretKeyFactory.getInstance(ALGORITHM_ENCRYPTED_VALUE)
val keyBytes = secretKeyFactory.generateSecret(pbKeySpec).encoded
val keySpec = SecretKeySpec(keyBytes, ALGORITHM_VALUE)
val ivRandom = SecureRandom()
val iv = ByteArray(16)
ivRandom.nextBytes(iv)
val ivSpec = IvParameterSpec(iv)
val cipher = Cipher.getInstance(TRANSFORMATION_ENCRYPTED_VALUE)
cipher.init(Cipher.ENCRYPT_MODE, keySpec, ivSpec)
val encrypted = cipher.doFinal(encryptedValue)
map["salt"] = salt
map["iv"] = iv
map["encrypted"] = encrypted
return map
}
fun decrypt(map: HashMap<String, ByteArray>): ByteArray {
var decrypted: ByteArray? = null
try {
val salt = map["salt"]
val iv = map["iv"]
val encrypted = map["encrypted"]
val passwordChar = ENCRYPTED_VALUE.toCharArray()
val pbKeySpec = PBEKeySpec(passwordChar, salt, 1324, 256)
val secretFactory = SecretKeyFactory.getInstance(ALGORITHM_ENCRYPTED_VALUE)
val keyBytes = secretFactory.generateSecret(pbKeySpec).encoded
val keySpec = SecretKeySpec(keyBytes, ALGORITHM_VALUE)
val cipher = Cipher.getInstance(TRANSFORMATION_ENCRYPTED_VALUE)
val ivSpec = IvParameterSpec(iv)
cipher.init(Cipher.DECRYPT_MODE, keySpec, ivSpec)
decrypted = cipher.doFinal(encrypted)
} catch (e: Exception) {
e.printStackTrace()
}
return decrypted!!
}
save & retrieve from sharepreference
fun Context.saveEmailToSharePreference(email: String) {
val preferences = getDefaultSharedPreferences(this)
val editor = preferences.edit()
editor.putString(AGENT_EMAIL, email)
editor.apply()
}
fun Context.getEmailFromSharePreference(): String? {
return getDefaultSharedPreferences(this)
.getString(AGENT_EMAIL, null)
}
//check internet access
/**
-
Check whether network is available
-
@return Whether device is connected to Network.
*/
fun Context.checkInternetAccess(): Boolean {
try {with(getSystemService(CONNECTIVITY_SERVICE) as ConnectivityManager) { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { //Device is running on Marshmallow or later Android OS. with(getNetworkCapabilities(activeNetwork)) { @Suppress("NULLABILITY_MISMATCH_BASED_ON_JAVA_ANNOTATIONS") return this!!.hasTransport(NetworkCapabilities.TRANSPORT_WIFI) || hasTransport( NetworkCapabilities.TRANSPORT_CELLULAR ) } } else { @Suppress("DEPRECATION") activeNetworkInfo?.let { // connected to the internet @Suppress("DEPRECATION") return listOf( ConnectivityManager.TYPE_WIFI, ConnectivityManager.TYPE_MOBILE ).contains(it.type) } } } return false
} catch (exc: NullPointerException) {
return false
}
}
@SuppressLint("SimpleDateFormat")
fun convertLongToTime(time: Long): String {
val date = Date(time)
val format = SimpleDateFormat(DATE_TIME_FORMAT)
return format.format(date)
}
fun getStringFromBitmap(imageView: ImageView): Bitmap {
imageView.invalidate()
val drawable = imageView.drawable as BitmapDrawable
return drawable.bitmap
}
//save image to phone memory and return the path
fun Context.saveToInternalStorageForFingerprint(
enrolmentId: String,
fingerprintName: String,
bitmapImage: Bitmap
): String {
println("Bit $bitmapImage")
val cw = ContextWrapper(applicationContext)
// path to /data/data/yourapp/app_data/imageDir
val directory = cw.getDir("fingerprint", Context.MODE_PRIVATE)
// Create imageDir
val mypath = File(directory, "${Date().time}-$fingerprintName-${enrolmentId}.jpg")
var fos: FileOutputStream? = null
try {
fos = FileOutputStream(mypath)
// Use the compress method on the BitMap object to write image to the OutputStream
bitmapImage.compress(Bitmap.CompressFormat.PNG, 100, fos)
} catch (e: java.lang.Exception) {
e.printStackTrace()
} finally {
try {
fos!!.close()
} catch (e: IOException) {
e.printStackTrace()
}
}
return mypath.absolutePath
}
//check if the device is rooted
fun findBinary(binaryName: String): Boolean {
var found = false
if (!found) {
val places = arrayOf("/sbin/", "/system/bin/", "/system/xbin/",
"/data/local/xbin/", "/data/local/bin/",
"/system/sd/xbin/", "/system/bin/failsafe/", "/data/local/")
for (where in places) {
if (File(where + binaryName).exists()) {
found = true
break
}
}
}
return found
}
fun isRooted(): Boolean {
return findBinary("su")
}
//initdate picker
fun Context.initDatePicker(dateEditText: EditText, calendar: Calendar) {
val date =
DatePickerDialog.OnDateSetListener { view, year, monthOfYear, dayOfMonth -> // TODO Auto-generated method stub
calendar.set(Calendar.YEAR, year)
calendar.set(Calendar.MONTH, monthOfYear)
calendar.set(Calendar.DAY_OF_MONTH, dayOfMonth)
updateLabel(dateEditText, calendar)
}
dateEditText.setOnClickListener {
val datePickerDialog = DatePickerDialog(this,
date,
calendar.get(Calendar.YEAR),
calendar.get(Calendar.MONTH),
calendar.get(
Calendar.DAY_OF_MONTH))
datePickerDialog.show()
datePickerDialog.getButton(DatePickerDialog.BUTTON_NEGATIVE).setTextColor(Color.GRAY);
datePickerDialog.getButton(DatePickerDialog.BUTTON_POSITIVE).setTextColor(Color.GRAY);
}
}
private fun updateLabel(dateField: EditText, calendar: Calendar) {
val myFormat = "dd/MM/yyyy"
val sdf = SimpleDateFormat(myFormat, Locale.US)
dateField.setText(sdf.format(calendar.time))
}
//round off decimal
fun roundOffDecimal(number: Double): Double? {
val df = DecimalFormat("#.##")
df.roundingMode = RoundingMode.CEILING
return df.format(number).toDouble()
}
//convert string to base64
fun convertBase64ToImage(encodedImage: String): Bitmap{
val pureEncodedImage = encodedImage.substring(encodedImage.indexOf(",") + 1)
val decodedString: ByteArray = Base64.decode(pureEncodedImage, Base64.DEFAULT)
return BitmapFactory.decodeByteArray(decodedString, 0, decodedString.size)
}
fun convertImageToBase64(bitmapImage: Bitmap):String{
val baos = ByteArrayOutputStream()
bitmapImage.compress(Bitmap.CompressFormat.JPEG, 100, baos) // bm is the bitmap object
val b: ByteArray = baos.toByteArray()
return Base64.encodeToString(b, Base64.DEFAULT)
}
//generate random number
fun generateProjectPrimaryNumber(): String? {
val random = Random()
val number = random.nextInt(9999999)
return String.format("%07d", number)
}
fun getImageFromInternalStorage(context: Context, imageFileName: String): Bitmap? {
val directory = context.filesDir
val file = File(directory, imageFileName)
return BitmapFactory.decodeStream(FileInputStream(file))
}
fun deleteImageFromInternalStorage(context: Context, imageFileName: String): Boolean {
val dir = context.filesDir
val file = File(dir, imageFileName)
return file.delete()
}
//phone resolution
fun Context.getPhoneResolutionValue(): String{
var result = ""
when(resources.configuration.screenLayout and Configuration.SCREENLAYOUT_SIZE_MASK){
Configuration.SCREENLAYOUT_SIZE_LARGE -> {
result = LARGE_SCREEN
}
Configuration.SCREENLAYOUT_SIZE_NORMAL ->{
result = NORMAL_SCREEN
}
Configuration.SCREENLAYOUT_SIZE_SMALL ->{
result = SMALL_SCREEN
}
}
return result
}
//Camerax demo with analysis
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.Manifest
import android.content.pm.PackageManager
import android.net.Uri
import android.util.Log
import android.view.View
import android.widget.Toast
import androidx.core.app.ActivityCompat
import androidx.core.content.ContextCompat
import java.util.concurrent.Executors
import androidx.camera.core.*
import androidx.camera.lifecycle.ProcessCameraProvider
import kotlinx.android.synthetic.main.activity_main.*
import java.io.File
import java.nio.ByteBuffer
import java.text.SimpleDateFormat
import java.util.*
import java.util.concurrent.ExecutorService
typealias LumaListener = (luma: Double) -> Unit
class MainActivity : AppCompatActivity() {
private var imageCapture: ImageCapture? = null
private lateinit var outputDirectory: File
private lateinit var cameraExecutor: ExecutorService
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
// Request camera permissions
if (allPermissionsGranted()) {
startCamera()
} else {
ActivityCompat.requestPermissions(
this, REQUIRED_PERMISSIONS, REQUEST_CODE_PERMISSIONS)
}
// Set up the listener for take photo button
camera_capture_button.setOnClickListener { takePhoto() }
outputDirectory = getOutputDirectory()
cameraExecutor = Executors.newSingleThreadExecutor()
}
private fun takePhoto() {
image.visibility = View.GONE
viewFinder.visibility = View.VISIBLE
println("take photo")
// Get a stable reference of the modifiable image capture use case
println("image capture $imageCapture")
val imageCapture = imageCapture ?: return
// Create time-stamped output file to hold the image
val photoFile = File(
outputDirectory,
SimpleDateFormat(FILENAME_FORMAT, Locale.US
).format(System.currentTimeMillis()) + ".jpg")
println("File $photoFile")
// Create output options object which contains file + metadata
val outputOptions = ImageCapture.OutputFileOptions.Builder(photoFile).build()
println("output $outputOptions")
// Set up image capture listener, which is triggered after photo has
// been taken
imageCapture.takePicture(
outputOptions, ContextCompat.getMainExecutor(this), object : ImageCapture.OnImageSavedCallback {
override fun onError(exc: ImageCaptureException) {
println("Error ${exc.message}")
Log.e(TAG, "Photo capture failed: ${exc.message}", exc)
}
override fun onImageSaved(output: ImageCapture.OutputFileResults) {
val savedUri = Uri.fromFile(photoFile)
viewFinder.visibility = View.GONE
image.visibility = View.VISIBLE
image.setImageURI(savedUri)
val msg = "Photo capture succeeded: $savedUri"
println("message $msg")
Toast.makeText(baseContext, msg, Toast.LENGTH_SHORT).show()
Log.d(TAG, msg)
}
})
}
private fun startCamera() {
val cameraProviderFuture = ProcessCameraProvider.getInstance(this)
cameraProviderFuture.addListener(Runnable {
// Used to bind the lifecycle of cameras to the lifecycle owner
val cameraProvider: ProcessCameraProvider = cameraProviderFuture.get()
// Preview
val preview = Preview.Builder()
.build()
.also {
it.setSurfaceProvider(viewFinder.createSurfaceProvider())
}
imageCapture = ImageCapture.Builder()
.build()
val imageAnalyzer = ImageAnalysis.Builder()
.build()
.also {
it.setAnalyzer(cameraExecutor, LuminosityAnalyzer { luma ->
Log.d(TAG, "Average luminosity: $luma")
})
}
// Select back camera as a default
val cameraSelector = CameraSelector.DEFAULT_BACK_CAMERA
try {
// Unbind use cases before rebinding
cameraProvider.unbindAll()
// Bind use cases to camera
cameraProvider.bindToLifecycle(
this, cameraSelector, preview, imageCapture, imageAnalyzer)
} catch(exc: Exception) {
Log.e(TAG, "Use case binding failed", exc)
}
}, ContextCompat.getMainExecutor(this))
}
private fun allPermissionsGranted() = REQUIRED_PERMISSIONS.all {
ContextCompat.checkSelfPermission(
baseContext, it) == PackageManager.PERMISSION_GRANTED
}
private fun getOutputDirectory(): File {
val mediaDir = externalMediaDirs.firstOrNull()?.let {
File(it, resources.getString(R.string.enrolment_id)).apply { mkdirs() } }
return if (mediaDir != null && mediaDir.exists())
mediaDir else filesDir
}
override fun onDestroy() {
super.onDestroy()
cameraExecutor.shutdown()
}
override fun onRequestPermissionsResult(
requestCode: Int, permissions: Array<String>, grantResults:
IntArray) {
if (requestCode == REQUEST_CODE_PERMISSIONS) {
if (allPermissionsGranted()) {
startCamera()
} else {
Toast.makeText(this,
"Permissions not granted by the user.",
Toast.LENGTH_SHORT).show()
finish()
}
}
}
companion object {
private const val TAG = "form_capture"
// private const val FILENAME_FORMAT = "yyyy-MM-dd-HH-mm-ss-SSS"
private const val FILENAME_FORMAT = "ddMMyyyy"
private const val ENROLMENT_ID = "123443444"
private const val REQUEST_CODE_PERMISSIONS = 10
private val REQUIRED_PERMISSIONS = arrayOf(Manifest.permission.CAMERA)
}
private class LuminosityAnalyzer(private val listener: LumaListener) : ImageAnalysis.Analyzer {
private fun ByteBuffer.toByteArray(): ByteArray {
rewind() // Rewind the buffer to zero
val data = ByteArray(remaining())
get(data) // Copy the buffer into a byte array
return data // Return the byte array
}
override fun analyze(image: ImageProxy) {
val buffer = image.planes[0].buffer
val data = buffer.toByteArray()
val pixels = data.map { it.toInt() and 0xFF }
val luma = pixels.average()
listener(luma)
image.close()
}
}
}
//Camerax demo with analysis
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.Manifest
import android.content.pm.PackageManager
import android.net.Uri
import android.util.Log
import android.view.View
import android.widget.Toast
import androidx.core.app.ActivityCompat
import androidx.core.content.ContextCompat
import java.util.concurrent.Executors
import androidx.camera.core.*
import androidx.camera.lifecycle.ProcessCameraProvider
import kotlinx.android.synthetic.main.activity_main.*
import java.io.File
import java.nio.ByteBuffer
import java.text.SimpleDateFormat
import java.util.*
import java.util.concurrent.ExecutorService
typealias LumaListener = (luma: Double) -> Unitclass MainActivity : AppCompatActivity() {
private var imageCapture: ImageCapture? = nullprivate lateinit var outputDirectory: File private lateinit var cameraExecutor: ExecutorService override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) // Request camera permissions if (allPermissionsGranted()) { startCamera() } else { ActivityCompat.requestPermissions( this, REQUIRED_PERMISSIONS, REQUEST_CODE_PERMISSIONS) } // Set up the listener for take photo button camera_capture_button.setOnClickListener { takePhoto() } outputDirectory = getOutputDirectory() cameraExecutor = Executors.newSingleThreadExecutor() } private fun takePhoto() { image.visibility = View.GONE viewFinder.visibility = View.VISIBLE println("take photo") // Get a stable reference of the modifiable image capture use case println("image capture $imageCapture") val imageCapture = imageCapture ?: return // Create time-stamped output file to hold the image val photoFile = File( outputDirectory, SimpleDateFormat(FILENAME_FORMAT, Locale.US ).format(System.currentTimeMillis()) + ".jpg") println("File $photoFile") // Create output options object which contains file + metadata val outputOptions = ImageCapture.OutputFileOptions.Builder(photoFile).build() println("output $outputOptions") // Set up image capture listener, which is triggered after photo has // been taken imageCapture.takePicture( outputOptions, ContextCompat.getMainExecutor(this), object : ImageCapture.OnImageSavedCallback { override fun onError(exc: ImageCaptureException) { println("Error ${exc.message}") Log.e(TAG, "Photo capture failed: ${exc.message}", exc) } override fun onImageSaved(output: ImageCapture.OutputFileResults) { val savedUri = Uri.fromFile(photoFile) viewFinder.visibility = View.GONE image.visibility = View.VISIBLE image.setImageURI(savedUri) val msg = "Photo capture succeeded: $savedUri" println("message $msg") Toast.makeText(baseContext, msg, Toast.LENGTH_SHORT).show() Log.d(TAG, msg) } }) } private fun startCamera() { val cameraProviderFuture = ProcessCameraProvider.getInstance(this) cameraProviderFuture.addListener(Runnable { // Used to bind the lifecycle of cameras to the lifecycle owner val cameraProvider: ProcessCameraProvider = cameraProviderFuture.get() // Preview val preview = Preview.Builder() .build() .also { it.setSurfaceProvider(viewFinder.createSurfaceProvider()) } imageCapture = ImageCapture.Builder() .build() val imageAnalyzer = ImageAnalysis.Builder() .build() .also { it.setAnalyzer(cameraExecutor, LuminosityAnalyzer { luma -> Log.d(TAG, "Average luminosity: $luma") }) } // Select back camera as a default val cameraSelector = CameraSelector.DEFAULT_BACK_CAMERA try { // Unbind use cases before rebinding cameraProvider.unbindAll() // Bind use cases to camera cameraProvider.bindToLifecycle( this, cameraSelector, preview, imageCapture, imageAnalyzer) } catch(exc: Exception) { Log.e(TAG, "Use case binding failed", exc) } }, ContextCompat.getMainExecutor(this)) } private fun allPermissionsGranted() = REQUIRED_PERMISSIONS.all { ContextCompat.checkSelfPermission( baseContext, it) == PackageManager.PERMISSION_GRANTED } private fun getOutputDirectory(): File { val mediaDir = externalMediaDirs.firstOrNull()?.let { File(it, resources.getString(R.string.enrolment_id)).apply { mkdirs() } } return if (mediaDir != null && mediaDir.exists()) mediaDir else filesDir } override fun onDestroy() { super.onDestroy() cameraExecutor.shutdown() } override fun onRequestPermissionsResult( requestCode: Int, permissions: Array<String>, grantResults: IntArray) { if (requestCode == REQUEST_CODE_PERMISSIONS) { if (allPermissionsGranted()) { startCamera() } else { Toast.makeText(this, "Permissions not granted by the user.", Toast.LENGTH_SHORT).show() finish() } } } companion object { private const val TAG = "form_capture" // private const val FILENAME_FORMAT = "yyyy-MM-dd-HH-mm-ss-SSS" private const val FILENAME_FORMAT = "ddMMyyyy" private const val ENROLMENT_ID = "123443444" private const val REQUEST_CODE_PERMISSIONS = 10 private val REQUIRED_PERMISSIONS = arrayOf(Manifest.permission.CAMERA) } private class LuminosityAnalyzer(private val listener: LumaListener) : ImageAnalysis.Analyzer { private fun ByteBuffer.toByteArray(): ByteArray { rewind() // Rewind the buffer to zero val data = ByteArray(remaining()) get(data) // Copy the buffer into a byte array return data // Return the byte array } override fun analyze(image: ImageProxy) { val buffer = image.planes[0].buffer val data = buffer.toByteArray() val pixels = data.map { it.toInt() and 0xFF } val luma = pixels.average() listener(luma) image.close() } }
}
//Camerax demo with analysis
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.Manifest
import android.content.pm.PackageManager
import android.net.Uri
import android.util.Log
import android.view.View
import android.widget.Toast
import androidx.core.app.ActivityCompat
import androidx.core.content.ContextCompat
import java.util.concurrent.Executors
import androidx.camera.core.*
import androidx.camera.lifecycle.ProcessCameraProvider
import kotlinx.android.synthetic.main.activity_main.*
import java.io.File
import java.nio.ByteBuffer
import java.text.SimpleDateFormat
import java.util.*
import java.util.concurrent.ExecutorService
typealias LumaListener = (luma: Double) -> Unit
class MainActivity : AppCompatActivity() {
private var imageCapture: ImageCapture? = nullprivate lateinit var outputDirectory: File private lateinit var cameraExecutor: ExecutorService override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) // Request camera permissions if (allPermissionsGranted()) { startCamera() } else { ActivityCompat.requestPermissions( this, REQUIRED_PERMISSIONS, REQUEST_CODE_PERMISSIONS) } // Set up the listener for take photo button camera_capture_button.setOnClickListener { takePhoto() } outputDirectory = getOutputDirectory() cameraExecutor = Executors.newSingleThreadExecutor() } private fun takePhoto() { image.visibility = View.GONE viewFinder.visibility = View.VISIBLE println("take photo") // Get a stable reference of the modifiable image capture use case println("image capture $imageCapture") val imageCapture = imageCapture ?: return // Create time-stamped output file to hold the image val photoFile = File( outputDirectory, SimpleDateFormat(FILENAME_FORMAT, Locale.US ).format(System.currentTimeMillis()) + ".jpg") println("File $photoFile") // Create output options object which contains file + metadata val outputOptions = ImageCapture.OutputFileOptions.Builder(photoFile).build() println("output $outputOptions") // Set up image capture listener, which is triggered after photo has // been taken imageCapture.takePicture( outputOptions, ContextCompat.getMainExecutor(this), object : ImageCapture.OnImageSavedCallback { override fun onError(exc: ImageCaptureException) { println("Error ${exc.message}") Log.e(TAG, "Photo capture failed: ${exc.message}", exc) } override fun onImageSaved(output: ImageCapture.OutputFileResults) { val savedUri = Uri.fromFile(photoFile) viewFinder.visibility = View.GONE image.visibility = View.VISIBLE image.setImageURI(savedUri) val msg = "Photo capture succeeded: $savedUri" println("message $msg") Toast.makeText(baseContext, msg, Toast.LENGTH_SHORT).show() Log.d(TAG, msg) } }) } private fun startCamera() { val cameraProviderFuture = ProcessCameraProvider.getInstance(this) cameraProviderFuture.addListener(Runnable { // Used to bind the lifecycle of cameras to the lifecycle owner val cameraProvider: ProcessCameraProvider = cameraProviderFuture.get() // Preview val preview = Preview.Builder() .build() .also { it.setSurfaceProvider(viewFinder.createSurfaceProvider()) } imageCapture = ImageCapture.Builder() .build() val imageAnalyzer = ImageAnalysis.Builder() .build() .also { it.setAnalyzer(cameraExecutor, LuminosityAnalyzer { luma -> Log.d(TAG, "Average luminosity: $luma") }) } // Select back camera as a default val cameraSelector = CameraSelector.DEFAULT_BACK_CAMERA try { // Unbind use cases before rebinding cameraProvider.unbindAll() // Bind use cases to camera cameraProvider.bindToLifecycle( this, cameraSelector, preview, imageCapture, imageAnalyzer) } catch(exc: Exception) { Log.e(TAG, "Use case binding failed", exc) } }, ContextCompat.getMainExecutor(this)) } private fun allPermissionsGranted() = REQUIRED_PERMISSIONS.all { ContextCompat.checkSelfPermission( baseContext, it) == PackageManager.PERMISSION_GRANTED } private fun getOutputDirectory(): File { val mediaDir = externalMediaDirs.firstOrNull()?.let { File(it, resources.getString(R.string.enrolment_id)).apply { mkdirs() } } return if (mediaDir != null && mediaDir.exists()) mediaDir else filesDir } override fun onDestroy() { super.onDestroy() cameraExecutor.shutdown() } override fun onRequestPermissionsResult( requestCode: Int, permissions: Array<String>, grantResults: IntArray) { if (requestCode == REQUEST_CODE_PERMISSIONS) { if (allPermissionsGranted()) { startCamera() } else { Toast.makeText(this, "Permissions not granted by the user.", Toast.LENGTH_SHORT).show() finish() } } } companion object { private const val TAG = "form_capture" // private const val FILENAME_FORMAT = "yyyy-MM-dd-HH-mm-ss-SSS" private const val FILENAME_FORMAT = "ddMMyyyy" private const val ENROLMENT_ID = "123443444" private const val REQUEST_CODE_PERMISSIONS = 10 private val REQUIRED_PERMISSIONS = arrayOf(Manifest.permission.CAMERA) } private class LuminosityAnalyzer(private val listener: LumaListener) : ImageAnalysis.Analyzer { private fun ByteBuffer.toByteArray(): ByteArray { rewind() // Rewind the buffer to zero val data = ByteArray(remaining()) get(data) // Copy the buffer into a byte array return data // Return the byte array } override fun analyze(image: ImageProxy) { val buffer = image.planes[0].buffer val data = buffer.toByteArray() val pixels = data.map { it.toInt() and 0xFF } val luma = pixels.average() listener(luma) image.close() } }
}
###CameraxApp demo without analysis
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.Manifest
import android.content.pm.PackageManager
import android.net.Uri
import android.util.Log
import android.view.View
import android.widget.Toast
import androidx.core.app.ActivityCompat
import androidx.core.content.ContextCompat
import java.util.concurrent.Executors
import androidx.camera.core.*
import androidx.camera.lifecycle.ProcessCameraProvider
import kotlinx.android.synthetic.main.activity_main.*
import java.io.File
import java.nio.ByteBuffer
import java.text.SimpleDateFormat
import java.util.*
import java.util.concurrent.ExecutorService
typealias LumaListener = (luma: Double) -> Unit
class MainActivity : AppCompatActivity() {
private var imageCapture: ImageCapture? = null
private lateinit var outputDirectory: File
private lateinit var cameraExecutor: ExecutorService
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
// Request camera permissions
if (allPermissionsGranted()) {
startCamera()
} else {
ActivityCompat.requestPermissions(
this, REQUIRED_PERMISSIONS, REQUEST_CODE_PERMISSIONS)
}
// Set up the listener for take photo button
camera_capture_button.setOnClickListener { takePhoto() }
outputDirectory = getOutputDirectory()
cameraExecutor = Executors.newSingleThreadExecutor()
}
private fun takePhoto() {
image.visibility = View.GONE
viewFinder.visibility = View.VISIBLE
println("take photo")
// Get a stable reference of the modifiable image capture use case
println("image capture $imageCapture")
val imageCapture = imageCapture ?: return
// Create time-stamped output file to hold the image
val photoFile = File(
outputDirectory,
SimpleDateFormat(FILENAME_FORMAT, Locale.US
).format(System.currentTimeMillis()) + ".jpg")
println("File $photoFile")
// Create output options object which contains file + metadata
val outputOptions = ImageCapture.OutputFileOptions.Builder(photoFile).build()
println("output $outputOptions")
// Set up image capture listener, which is triggered after photo has
// been taken
imageCapture.takePicture(
outputOptions, ContextCompat.getMainExecutor(this), object : ImageCapture.OnImageSavedCallback {
override fun onError(exc: ImageCaptureException) {
println("Error ${exc.message}")
Log.e(TAG, "Photo capture failed: ${exc.message}", exc)
}
override fun onImageSaved(output: ImageCapture.OutputFileResults) {
val savedUri = Uri.fromFile(photoFile)
viewFinder.visibility = View.GONE
image.visibility = View.VISIBLE
image.setImageURI(savedUri)
val msg = "Photo capture succeeded: $savedUri"
println("message $msg")
Toast.makeText(baseContext, msg, Toast.LENGTH_SHORT).show()
Log.d(TAG, msg)
}
})
}
private fun startCamera() {
val cameraProviderFuture = ProcessCameraProvider.getInstance(this)
cameraProviderFuture.addListener(Runnable {
// Used to bind the lifecycle of cameras to the lifecycle owner
val cameraProvider: ProcessCameraProvider = cameraProviderFuture.get()
// Preview
val preview = Preview.Builder()
.build()
.also {
it.setSurfaceProvider(viewFinder.createSurfaceProvider())
}
imageCapture = ImageCapture.Builder()
.build()
// val imageAnalyzer = ImageAnalysis.Builder()
// .build()
// .also {
// it.setAnalyzer(cameraExecutor, LuminosityAnalyzer { luma ->
// Log.d(TAG, "Average luminosity: $luma")
// })
// }
// Select back camera as a default
val cameraSelector = CameraSelector.DEFAULT_BACK_CAMERA
try {
// Unbind use cases before rebinding
cameraProvider.unbindAll()
// Bind use cases to camera
cameraProvider.bindToLifecycle(
this, cameraSelector, preview, imageCapture)
} catch(exc: Exception) {
Log.e(TAG, "Use case binding failed", exc)
}
}, ContextCompat.getMainExecutor(this))
}
private fun allPermissionsGranted() = REQUIRED_PERMISSIONS.all {
ContextCompat.checkSelfPermission(
baseContext, it) == PackageManager.PERMISSION_GRANTED
}
private fun getOutputDirectory(): File {
val mediaDir = externalMediaDirs.firstOrNull()?.let {
File(it, resources.getString(R.string.enrolment_id)).apply { mkdirs() } }
return if (mediaDir != null && mediaDir.exists())
mediaDir else filesDir
}
override fun onDestroy() {
super.onDestroy()
cameraExecutor.shutdown()
}
override fun onRequestPermissionsResult(
requestCode: Int, permissions: Array<String>, grantResults:
IntArray) {
if (requestCode == REQUEST_CODE_PERMISSIONS) {
if (allPermissionsGranted()) {
startCamera()
} else {
Toast.makeText(this,
"Permissions not granted by the user.",
Toast.LENGTH_SHORT).show()
finish()
}
}
}
companion object {
private const val TAG = "form_capture"
// private const val FILENAME_FORMAT = "yyyy-MM-dd-HH-mm-ss-SSS"
private const val FILENAME_FORMAT = "ddMMyyyy"
private const val ENROLMENT_ID = "123443444"
private const val REQUEST_CODE_PERMISSIONS = 10
private val REQUIRED_PERMISSIONS = arrayOf(Manifest.permission.CAMERA)
}
private class LuminosityAnalyzer(private val listener: LumaListener) : ImageAnalysis.Analyzer {
private fun ByteBuffer.toByteArray(): ByteArray {
rewind() // Rewind the buffer to zero
val data = ByteArray(remaining())
get(data) // Copy the buffer into a byte array
return data // Return the byte array
}
override fun analyze(image: ImageProxy) {
val buffer = image.planes[0].buffer
val data = buffer.toByteArray()
val pixels = data.map { it.toInt() and 0xFF }
val luma = pixels.average()
listener(luma)
image.close()
}
}
}
fun Context.deleteSharePreference(key: String) {
val settings: SharedPreferences = getDefaultSharedPreferences(this)
settings.edit().remove(key).apply()
}
//check if gps & network is enabled
fun checkGPSNetwork():Boolean{
val lm = getSystemService(LOCATION_SERVICE) as LocationManager
var gps_enabled = false
var network_enabled = false