diff --git a/Libraries.txt b/Libraries.txt
index a03f7760..3c8fdcd3 100644
--- a/Libraries.txt
+++ b/Libraries.txt
@@ -1,4 +1,4 @@
-Open Source libraries used in the Scanbot SDK for Android version 8.1.0
+Open Source libraries used in the Scanbot SDK for Android version 9.0.0
 
 CWAC-Camera
 
@@ -1971,12 +1971,12 @@ defined by AIM ITS/04-023 International Technical Standard - Extended Channel In
 
 magic-enum
 
-Version v0.8.1
+Version v0.9.7
 (https://github.com/Neargye/magic_enum)
 
 MIT License
 
-Copyright (c) 2019 - 2022 Daniil Goncharov
+Copyright (c) 2019 - 2024 Daniil Goncharov
 
 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal
diff --git a/README.md b/README.md
index 7550815f..a6d3d77e 100644
--- a/README.md
+++ b/README.md
@@ -25,7 +25,7 @@ Make sure you have the latest stable version of [Android Studio](https://develop
 
 2. There are 4 separate folders with standalone examples:  
 
-	* **classic-components-example**: Example project for the Scanbot SDK Classic Components which allow for full customization. 
+	* **classic-components-example**: Example project for the Scanbot SDK Classic Components which allow for full customization.
 	* **compose-custom-ui-example**: Example project for the Scanbot SDK Compose Custom Components which allow for full customization.
 	* **document-scanner-ready-to-use-ui-example:** Example project for the Scanbot Document Scanner SDK using our Ready-To-Use UI components.
 	* **data-capture-ready-to-use-ui-example**: Example project showcasing the Scanbot Data Capture Modules using our Ready-to-Use UI components.
diff --git a/classic-components-example/README.md b/classic-components-example/README.md
new file mode 100644
index 00000000..05ee2654
--- /dev/null
+++ b/classic-components-example/README.md
@@ -0,0 +1,11 @@
+# Scanbot SDK Classic Components examples
+
+This project contains multiple standalone Android app modules demonstrating the Scanbot SDK Classic Components. Each module can be opened and run on its own. The only shared code lives in the `common` module.
+
+## How to run a module
+
+1. Open `scanbot-sdk-example-android/classic-components-example` in Android Studio.
+2. Sync Gradle.
+3. Choose one module in the **Run** configuration (each module is an `application`).
+4. Add your Scanbot SDK license key in the module’s `ExampleApplication` or stay on demo mode.
+5. Run the app on a device or emulator.
diff --git a/classic-components-example/adjustable-filters/build.gradle b/classic-components-example/adjustable-filters/build.gradle
index 9b457015..8333f97c 100644
--- a/classic-components-example/adjustable-filters/build.gradle
+++ b/classic-components-example/adjustable-filters/build.gradle
@@ -17,21 +17,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(':common'))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/adjustable-filters/proguard-rules.pro b/classic-components-example/adjustable-filters/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/adjustable-filters/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/adjustable-filters/src/main/java/io/scanbot/example/FilterActivity.kt b/classic-components-example/adjustable-filters/src/main/java/io/scanbot/example/FilterActivity.kt
index facb3372..ee30d555 100644
--- a/classic-components-example/adjustable-filters/src/main/java/io/scanbot/example/FilterActivity.kt
+++ b/classic-components-example/adjustable-filters/src/main/java/io/scanbot/example/FilterActivity.kt
@@ -25,8 +25,8 @@ import io.scanbot.sdk.imageprocessing.ParametricFilter
 import kotlinx.coroutines.*
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
diff --git a/classic-components-example/adjustable-filters/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/adjustable-filters/src/main/java/io/scanbot/example/MainActivity.kt
index 8604397d..27519171 100755
--- a/classic-components-example/adjustable-filters/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/adjustable-filters/src/main/java/io/scanbot/example/MainActivity.kt
@@ -22,8 +22,8 @@ import kotlinx.coroutines.Dispatchers
 import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 /**
- Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
- Please, check the official documentation for more details:
+ This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+ Please check the official documentation for more details:
  Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
  ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -105,9 +105,16 @@ class MainActivity : AppCompatActivity() {
 
     private suspend fun createAndScanDocumentPage(imageUri: Uri): String? {
         val imageRef = withContext(Dispatchers.IO) {
-            val inputStream = contentResolver.openInputStream(imageUri)
-                ?: throw Exception("Cannot open input stream from URI")
-            ImageRef.fromInputStream(inputStream)
+            contentResolver.openInputStream(imageUri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
+            }
+        }
+        if (imageRef == null) {
+            withContext(Dispatchers.Main) {
+                Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $imageUri")
+                showToast("Error opening selected image!")
+            }
+            return null
         }
 
         val sdk = ScanbotSDK(this)
diff --git a/classic-components-example/barcode-scanner/build.gradle b/classic-components-example/barcode-scanner/build.gradle
index d9b844d8..b528e561 100644
--- a/classic-components-example/barcode-scanner/build.gradle
+++ b/classic-components-example/barcode-scanner/build.gradle
@@ -15,13 +15,9 @@ android {
         versionName = "1.0"
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
@@ -32,6 +28,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScanAndCountViewActivity.kt b/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScanAndCountViewActivity.kt
index 7f3afb5e..abb9d86a 100644
--- a/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScanAndCountViewActivity.kt
+++ b/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScanAndCountViewActivity.kt
@@ -50,7 +50,11 @@ class BarcodeScanAndCountViewActivity : AppCompatActivity() {
         scanButton = findViewById(R.id.snapButton)
         nextButton = findViewById(R.id.nextButton)
         snapResult = findViewById(R.id.snapped_message)
-
+        val flashButton: Button = findViewById(R.id.flash)
+        flashButton.setOnClickListener {
+            flashEnabled = !flashEnabled
+            scanCountView.viewController.useFlash(flashEnabled)
+        }
         ScanbotSDK(this).createBarcodeScanner().onSuccess { scanner ->
 
             scanner.setConfiguration(scanner.copyCurrentConfiguration().copy().apply {
diff --git a/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScannerActivity.kt b/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScannerActivity.kt
index 9cc8fa68..fde3cbb3 100644
--- a/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScannerActivity.kt
+++ b/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScannerActivity.kt
@@ -7,6 +7,7 @@ import android.graphics.Bitmap
 import android.graphics.BitmapFactory
 import android.graphics.Matrix
 import android.os.Bundle
+import android.widget.Button
 import android.widget.ImageView
 import android.widget.Toast
 import androidx.appcompat.app.AppCompatActivity
@@ -51,7 +52,11 @@ class BarcodeScannerActivity : AppCompatActivity(), BarcodeScannerFrameHandler.R
         cameraView = findViewById(R.id.camera)
         resultView = findViewById(R.id.result)
         finderOverlay = findViewById(R.id.finder_overlay)
-
+        val flashButton: Button = findViewById(R.id.flash)
+        flashButton.setOnClickListener {
+            flashEnabled = !flashEnabled
+            cameraView.useFlash(flashEnabled)
+        }
         cameraView.setCameraOpenCallback {
             cameraView.postDelayed({
                 cameraView.useFlash(flashEnabled)
diff --git a/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScannerViewActivity.kt b/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScannerViewActivity.kt
index 7a38a12e..ff89a35c 100644
--- a/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScannerViewActivity.kt
+++ b/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/BarcodeScannerViewActivity.kt
@@ -4,17 +4,13 @@ import android.Manifest
 import android.content.Intent
 import android.content.pm.PackageManager
 import android.os.Bundle
-import android.view.View
-import android.view.ViewGroup
+import android.widget.Button
 import android.widget.ImageView
 import android.widget.Toast
 import androidx.appcompat.app.AppCompatActivity
 import androidx.core.app.ActivityCompat
 import androidx.core.content.ContextCompat
-import androidx.core.view.ViewCompat
 import androidx.core.view.WindowCompat
-import androidx.core.view.WindowInsetsCompat
-import androidx.core.view.updateLayoutParams
 import io.scanbot.common.Result
 import io.scanbot.common.onFailure
 import io.scanbot.common.onSuccess
@@ -48,7 +44,11 @@ class BarcodeScannerViewActivity : AppCompatActivity() {
 
         barcodeScannerView = findViewById(R.id.barcode_scanner_view)
         resultView = findViewById(R.id.result)
-
+        val flashButton: Button = findViewById(R.id.flash)
+        flashButton.setOnClickListener {
+            flashEnabled = !flashEnabled
+            barcodeScannerView.viewController.useFlash(flashEnabled)
+        }
         ScanbotSDK(this).createBarcodeScanner().onSuccess { scanner ->
             scanner.setConfiguration(scanner.copyCurrentConfiguration().copy().apply {
                 setBarcodeFormats(barcodeFormats = BarcodeTypeRepository.selectedTypes.toList())
@@ -88,7 +88,11 @@ class BarcodeScannerViewActivity : AppCompatActivity() {
                             image: ImageRef,
                             captureInfo: CaptureInfo
                         ) {
-                            TODO("Not yet implemented")
+                            image.toBitmap().onSuccess { bitmap ->
+                                resultView.post {
+                                    resultView.setImageBitmap(bitmap)
+                                }
+                            }
                         }
 
                         override fun onSelectionOverlayBarcodeClicked(barcodeItem: BarcodeItem) {
@@ -107,7 +111,6 @@ class BarcodeScannerViewActivity : AppCompatActivity() {
 
     override fun onResume() {
         super.onResume()
-        barcodeScannerView.viewController.onResume()
         if (ContextCompat.checkSelfPermission(
                 this,
                 Manifest.permission.CAMERA
@@ -122,11 +125,6 @@ class BarcodeScannerViewActivity : AppCompatActivity() {
         }
     }
 
-    override fun onPause() {
-        super.onPause()
-        barcodeScannerView.viewController.onPause()
-    }
-
     private fun handleSuccess(result: BarcodeScannerResult) {
         result.takeIf { it.barcodes.isNotEmpty() }?.let {
             BarcodeResultRepository.barcodeResultBundle = BarcodeResultBundle(result)
diff --git a/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/MainActivity.kt b/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/MainActivity.kt
index b92d96a5..ebd15f03 100644
--- a/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/MainActivity.kt
+++ b/classic-components-example/barcode-scanner/src/main/java/io/scanbot/example/ui/MainActivity.kt
@@ -28,8 +28,8 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -101,14 +101,25 @@ class MainActivity : AppCompatActivity() {
             binding.progressBar.isVisible = true
         }
 
-        withContext(Dispatchers.Default) {
-            val inputStream = contentResolver.openInputStream(uri) ?: throw IllegalStateException("Cannot open input stream from URI: $uri")
-            val imageRef = ImageRef.fromInputStream(inputStream)
+        val imageRef = withContext(Dispatchers.IO) {
+            contentResolver.openInputStream(uri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
+            }
+        }
+        if (imageRef == null) {
+            withContext(Dispatchers.Main) {
+                binding.progressBar.isVisible = false
+                showToast("Error opening selected image!")
+                Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $uri")
+            }
+            return
+        }
 
+        withContext(Dispatchers.Default) {
             val scanner = scanbotSdk.createBarcodeScanner().getOrThrow()
             scanner.setConfiguration(scanner.copyCurrentConfiguration().copy().apply {
                 setBarcodeFormats(barcodeFormats = BarcodeTypeRepository.selectedTypes.toList())
-            } )
+            })
             val result = scanner.run(imageRef).getOrNull()
 
             BarcodeResultRepository.barcodeResultBundle = result?.let { BarcodeResultBundle(it, imageRef) }
diff --git a/classic-components-example/build.gradle b/classic-components-example/build.gradle
index c3b0b6fa..e1b69f18 100644
--- a/classic-components-example/build.gradle
+++ b/classic-components-example/build.gradle
@@ -1,5 +1,5 @@
 plugins {
-    id("com.android.application") version "8.3.2" apply false
+    id("com.android.application") version "8.9.1" apply false
     id("com.android.library") version "8.3.2" apply false
     id("org.jetbrains.kotlin.android") version "2.2.20" apply false
 }
@@ -10,12 +10,12 @@ allprojects {
         submodulesNamespace = "io.scanbot.example"
 
         compileSdkVersion = 36
-        minSdkVersion = 21
+        minSdkVersion = 23
         targetSdkVersion = 35
 
         jvmToolchainVersion = 17
 
-        scanbotSdkVersion = "8.1.0"
+        scanbotSdkVersion = "9.0.0.1206-SNAPSHOT"
 
         androidCoreKtxVersion = "1.6.0"
         constraintLayoutVersion = "2.0.4"
diff --git a/classic-components-example/camera-fragment/build.gradle b/classic-components-example/camera-fragment/build.gradle
index 848c9e51..349e84f5 100644
--- a/classic-components-example/camera-fragment/build.gradle
+++ b/classic-components-example/camera-fragment/build.gradle
@@ -15,13 +15,9 @@ android {
         versionName = "1.0"
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
@@ -40,6 +36,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/camera-fragment/proguard-rules.pro b/classic-components-example/camera-fragment/proguard-rules.pro
deleted file mode 100755
index a988b426..00000000
--- a/classic-components-example/camera-fragment/proguard-rules.pro
+++ /dev/null
@@ -1,17 +0,0 @@
-# Add project specific ProGuard rules here.
-# By default, the flags in this file are appended to flags specified
-# in /Users/artem.kubiria/Development/sdk/tools/proguard/proguard-android.txt
-# You can edit the include path and order by changing the proguardFiles
-# directive in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# Add any project specific keep options here:
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
diff --git a/classic-components-example/camera-fragment/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/camera-fragment/src/main/java/io/scanbot/example/MainActivity.kt
index 7d6927a6..37bf2c88 100755
--- a/classic-components-example/camera-fragment/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/camera-fragment/src/main/java/io/scanbot/example/MainActivity.kt
@@ -25,8 +25,8 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -115,12 +115,15 @@ class MainActivity : AppCompatActivity() {
         }
 
         val documentImage = withContext(Dispatchers.Default) {
-            catchWithResult {
-                // load the selected image:
-                val inputStream = contentResolver.openInputStream(imageUri)
-                    ?: throw IllegalStateException("Cannot open input stream from URI: $imageUri")
-                val image = ImageRef.fromInputStream(inputStream)
+            val image = contentResolver.openInputStream(imageUri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
+            }
+            if (image == null) {
+                Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $imageUri")
+                return@withContext null
+            }
 
+            catchWithResult {
                 // create a new Document object with given image as original image:
                 val newDocument = scanbotSdk.documentApi.createDocument()
                     .getOrReturn() // can be handled with .getOrNull() if needed
@@ -144,6 +147,10 @@ class MainActivity : AppCompatActivity() {
 
         withContext(Dispatchers.Main) {
             progressBar.visibility = View.GONE
+            if (documentImage == null) {
+                this@MainActivity.showToast("Error opening selected image!")
+                return@withContext
+            }
             // show Page's document image:
             importResultImage.setImageBitmap(documentImage)
             importResultImage.visibility = View.VISIBLE
diff --git a/classic-components-example/camera-view-aspect-ratio-finder/build.gradle b/classic-components-example/camera-view-aspect-ratio-finder/build.gradle
index baf5c167..349e84f5 100644
--- a/classic-components-example/camera-view-aspect-ratio-finder/build.gradle
+++ b/classic-components-example/camera-view-aspect-ratio-finder/build.gradle
@@ -17,16 +17,12 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     packagingOptions {
         exclude 'META-INF/LICENSE.txt'
         exclude 'META-INF/LICENSE'
@@ -40,6 +36,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/camera-view-aspect-ratio-finder/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/camera-view-aspect-ratio-finder/src/main/java/io/scanbot/example/MainActivity.kt
index 4ecce016..5b11e8df 100755
--- a/classic-components-example/camera-view-aspect-ratio-finder/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/camera-view-aspect-ratio-finder/src/main/java/io/scanbot/example/MainActivity.kt
@@ -36,8 +36,8 @@ import io.scanbot.sdk.ui.camera.ShutterButton
 import io.scanbot.sdk.util.PolygonHelper
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -53,7 +53,7 @@ class MainActivity : AppCompatActivity(), DocumentScannerFrameHandler.ResultHand
 
     private var flashEnabled = false
     private var lastUserGuidanceHintTs = 0L
-    private val requiredPageAspectRatios = listOf(AspectRatio(4.0, 3.0))
+    private val requiredPageAspectRatios = listOf(AspectRatio(86.0, 53.0))
 
     override fun onCreate(savedInstanceState: Bundle?) {
         supportRequestWindowFeature(WindowCompat.FEATURE_ACTION_BAR_OVERLAY)
@@ -64,11 +64,11 @@ class MainActivity : AppCompatActivity(), DocumentScannerFrameHandler.ResultHand
 
         askPermission()
         setContentView(R.layout.activity_main)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(this.findViewById(R.id.root_view))
-
         cameraView = findViewById<View>(R.id.camera) as ScanbotCameraXView
         cameraView.setPreviewMode(CameraPreviewMode.FILL_IN)
+        cameraView.isSnapAnimationEnabled(true)
 
         // Lock the orientation of the UI (Activity) as well as the orientation of the taken picture to portrait.
         cameraView.lockToPortrait(true)
diff --git a/classic-components-example/camera-view-aspect-ratio-finder/src/main/res/values/strings.xml b/classic-components-example/camera-view-aspect-ratio-finder/src/main/res/values/strings.xml
index 21db9902..cce69b24 100755
--- a/classic-components-example/camera-view-aspect-ratio-finder/src/main/res/values/strings.xml
+++ b/classic-components-example/camera-view-aspect-ratio-finder/src/main/res/values/strings.xml
@@ -1,6 +1,6 @@
 <resources>
     <string name="app_name">Scanbot SDK Example</string>
 
-    <string name="hello_world">Hello world!</string>
+
     <string name="action_settings">Settings</string>
 </resources>
diff --git a/classic-components-example/camera-view/build.gradle b/classic-components-example/camera-view/build.gradle
index baf5c167..349e84f5 100644
--- a/classic-components-example/camera-view/build.gradle
+++ b/classic-components-example/camera-view/build.gradle
@@ -17,16 +17,12 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     packagingOptions {
         exclude 'META-INF/LICENSE.txt'
         exclude 'META-INF/LICENSE'
@@ -40,6 +36,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/camera-view/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/camera-view/src/main/java/io/scanbot/example/MainActivity.kt
index 0cd1654d..0df39e65 100755
--- a/classic-components-example/camera-view/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/camera-view/src/main/java/io/scanbot/example/MainActivity.kt
@@ -43,8 +43,8 @@ import io.scanbot.sdk.ui.camera.ShutterButton
 import io.scanbot.sdk.util.PolygonHelper
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -63,13 +63,13 @@ class MainActivity : AppCompatActivity(), DocumentScannerFrameHandler.ResultHand
     private var lastUserGuidanceHintTs = 0L
     private var flashEnabled = false
     private var autoSnappingEnabled = true
-    private val ignoreOrientationMistmatch = true
+    private val ignoreOrientationMismatch = true
     override fun onCreate(savedInstanceState: Bundle?) {
         supportRequestWindowFeature(WindowCompat.FEATURE_ACTION_BAR_OVERLAY)
         super.onCreate(savedInstanceState)
         askPermission()
         setContentView(R.layout.activity_main)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
 
         applyEdgeToEdge(this.findViewById(R.id.root_view))
         cameraView = findViewById<View>(R.id.camera) as ScanbotCameraXView
@@ -83,7 +83,7 @@ class MainActivity : AppCompatActivity(), DocumentScannerFrameHandler.ResultHand
                 // Please note: https://docs.scanbot.io/document-scanner-sdk/android/features/document-scanner/ui-components/
                 setConfiguration(copyCurrentConfiguration().apply {
                     parameters.apply {
-                        this.ignoreOrientationMismatch = ignoreOrientationMistmatch
+                        this.ignoreOrientationMismatch = ignoreOrientationMismatch
                         this.acceptedSizeScore = 75
                         this.acceptedAngleScore = 60
                     }
@@ -150,11 +150,11 @@ class MainActivity : AppCompatActivity(), DocumentScannerFrameHandler.ResultHand
                 )
             }
         }.onFailure { error ->
-            when(error){
-                is Result.InvalidLicenseError ->{
+            when (error) {
+                is Result.InvalidLicenseError -> {
                     Toast.makeText(this@MainActivity, "License is invalid: ${error.message}", Toast.LENGTH_LONG).show()
                 }
-                else ->  {
+                else -> {
                     Toast.makeText(this@MainActivity, "${error.message}", Toast.LENGTH_LONG).show()
                 }
             }
@@ -224,7 +224,7 @@ class MainActivity : AppCompatActivity(), DocumentScannerFrameHandler.ResultHand
             }
 
             DocumentDetectionStatus.OK_BUT_BAD_ASPECT_RATIO -> {
-                if (ignoreOrientationMistmatch) {
+                if (ignoreOrientationMismatch) {
                     userGuidanceHint.text = "Don't move"
                     // change polygon color to "OK"
                     polygonView.setFillColor(POLYGON_FILL_COLOR_OK)
diff --git a/classic-components-example/camera-view/src/main/res/values/strings.xml b/classic-components-example/camera-view/src/main/res/values/strings.xml
index 21db9902..cce69b24 100755
--- a/classic-components-example/camera-view/src/main/res/values/strings.xml
+++ b/classic-components-example/camera-view/src/main/res/values/strings.xml
@@ -1,6 +1,6 @@
 <resources>
     <string name="app_name">Scanbot SDK Example</string>
 
-    <string name="hello_world">Hello world!</string>
+
     <string name="action_settings">Settings</string>
 </resources>
diff --git a/classic-components-example/check-scanner/build.gradle b/classic-components-example/check-scanner/build.gradle
index 4f4ef646..27bb0e33 100644
--- a/classic-components-example/check-scanner/build.gradle
+++ b/classic-components-example/check-scanner/build.gradle
@@ -17,16 +17,12 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     packagingOptions {
         exclude 'META-INF/LICENSE.txt'
         exclude 'META-INF/LICENSE'
@@ -40,6 +36,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation fileTree(include: ['*.jar'], dir: 'libs')
     implementation(project(":common"))
diff --git a/classic-components-example/check-scanner/proguard-rules.pro b/classic-components-example/check-scanner/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/check-scanner/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/check-scanner/src/main/java/io/scanbot/example/AutoSnappingCheckRecognizerActivity.kt b/classic-components-example/check-scanner/src/main/java/io/scanbot/example/AutoSnappingCheckRecognizerActivity.kt
index f5df0939..71d08e9e 100644
--- a/classic-components-example/check-scanner/src/main/java/io/scanbot/example/AutoSnappingCheckRecognizerActivity.kt
+++ b/classic-components-example/check-scanner/src/main/java/io/scanbot/example/AutoSnappingCheckRecognizerActivity.kt
@@ -39,7 +39,7 @@ class AutoSnappingCheckScannerActivity : AppCompatActivity() {
         supportRequestWindowFeature(WindowCompat.FEATURE_ACTION_BAR_OVERLAY)
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_autosnapping_check_scanner)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(this.findViewById(R.id.root_view))
 
         cameraView = findViewById<ScanbotCameraXView>(R.id.camera).also { cameraView ->
diff --git a/classic-components-example/check-scanner/src/main/java/io/scanbot/example/CheckScannerActivity.kt b/classic-components-example/check-scanner/src/main/java/io/scanbot/example/CheckScannerActivity.kt
index d9cf7677..9ac8bf25 100644
--- a/classic-components-example/check-scanner/src/main/java/io/scanbot/example/CheckScannerActivity.kt
+++ b/classic-components-example/check-scanner/src/main/java/io/scanbot/example/CheckScannerActivity.kt
@@ -31,7 +31,7 @@ class CheckScannerActivity : AppCompatActivity() {
         supportRequestWindowFeature(WindowCompat.FEATURE_ACTION_BAR_OVERLAY)
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_check_scanner)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(this.findViewById(R.id.root_view))
 
         cameraView = findViewById<ScanbotCameraXView>(R.id.camera).also { cameraView ->
diff --git a/classic-components-example/check-scanner/src/main/java/io/scanbot/example/CheckScannerResultActivity.kt b/classic-components-example/check-scanner/src/main/java/io/scanbot/example/CheckScannerResultActivity.kt
index a0fd2d03..7e6cedb1 100644
--- a/classic-components-example/check-scanner/src/main/java/io/scanbot/example/CheckScannerResultActivity.kt
+++ b/classic-components-example/check-scanner/src/main/java/io/scanbot/example/CheckScannerResultActivity.kt
@@ -19,7 +19,7 @@ class CheckScannerResultActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_check_result)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(this.findViewById(R.id.root_view))
 
         val fieldsLayout = findViewById<LinearLayout>(R.id.check_result_fields_layout)
diff --git a/classic-components-example/check-scanner/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/check-scanner/src/main/java/io/scanbot/example/MainActivity.kt
index d42d517d..de3ed48e 100644
--- a/classic-components-example/check-scanner/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/check-scanner/src/main/java/io/scanbot/example/MainActivity.kt
@@ -25,8 +25,8 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -77,10 +77,21 @@ class MainActivity : AppCompatActivity() {
     private suspend fun scanCheck(uri: Uri) {
         withContext(Dispatchers.Main) { binding.progressBar.isVisible = true }
 
-        val result = withContext(Dispatchers.Default) {
-            val inputStream = contentResolver.openInputStream(uri) ?: throw IllegalStateException("Cannot open input stream from URI: $uri")
-            val imageRef = ImageRef.fromInputStream(inputStream)
+        val imageRef = withContext(Dispatchers.IO) {
+            contentResolver.openInputStream(uri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
+            }
+        }
+        if (imageRef == null) {
+            withContext(Dispatchers.Main) {
+                binding.progressBar.isVisible = false
+                showToast("Error opening selected image!")
+                Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $uri")
+            }
+            return
+        }
 
+        val result = withContext(Dispatchers.Default) {
             val scanner = scanbotSdk.createCheckScanner().getOrThrow()
             scanner.run(imageRef).getOrNull()
         }
diff --git a/classic-components-example/common/build.gradle b/classic-components-example/common/build.gradle
index e2a1776f..ef52fd20 100644
--- a/classic-components-example/common/build.gradle
+++ b/classic-components-example/common/build.gradle
@@ -9,14 +9,11 @@ android {
 
     defaultConfig {
         minSdk = project.ext.minSdkVersion
-
-        proguardFiles(getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro", "consumer-rules.pro")
     }
 
     buildTypes {
         named("release") {
             minifyEnabled = false
-            proguardFiles(getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro")
         }
     }
 
diff --git a/classic-components-example/common/consumer-rules.pro b/classic-components-example/common/consumer-rules.pro
deleted file mode 100644
index e69de29b..00000000
diff --git a/classic-components-example/common/proguard-rules.pro b/classic-components-example/common/proguard-rules.pro
deleted file mode 100644
index 481bb434..00000000
--- a/classic-components-example/common/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
\ No newline at end of file
diff --git a/classic-components-example/creditcard-scanner/build.gradle b/classic-components-example/creditcard-scanner/build.gradle
index f35fdc58..e573db84 100755
--- a/classic-components-example/creditcard-scanner/build.gradle
+++ b/classic-components-example/creditcard-scanner/build.gradle
@@ -17,21 +17,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/creditcard-scanner/proguard-rules.pro b/classic-components-example/creditcard-scanner/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/creditcard-scanner/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/creditcard-scanner/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/creditcard-scanner/src/main/java/io/scanbot/example/MainActivity.kt
index 5bf14381..329ac035 100755
--- a/classic-components-example/creditcard-scanner/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/creditcard-scanner/src/main/java/io/scanbot/example/MainActivity.kt
@@ -13,8 +13,8 @@ import androidx.core.content.ContextCompat
 import io.scanbot.example.common.applyEdgeToEdge
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
diff --git a/classic-components-example/creditcard-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt b/classic-components-example/creditcard-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
index d1997654..7cf9ffc7 100644
--- a/classic-components-example/creditcard-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
+++ b/classic-components-example/creditcard-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
@@ -28,7 +28,7 @@ class ScannerActivity : AppCompatActivity() {
         super.onCreate(savedInstanceState)
         binding = ActivityScannerBinding.inflate(layoutInflater)
         setContentView(binding.root)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(this.findViewById(R.id.root_view))
 
         // init scanbot sdk and create credit card scanner
diff --git a/classic-components-example/document-data-extractor-autosnapping/build.gradle b/classic-components-example/document-data-extractor-autosnapping/build.gradle
index 04891c60..b6dad455 100644
--- a/classic-components-example/document-data-extractor-autosnapping/build.gradle
+++ b/classic-components-example/document-data-extractor-autosnapping/build.gradle
@@ -17,21 +17,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/document-data-extractor-autosnapping/proguard-rules.pro b/classic-components-example/document-data-extractor-autosnapping/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/document-data-extractor-autosnapping/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/document-data-extractor-autosnapping/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/document-data-extractor-autosnapping/src/main/java/io/scanbot/example/MainActivity.kt
index 0f0d3c65..2038fdad 100755
--- a/classic-components-example/document-data-extractor-autosnapping/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/document-data-extractor-autosnapping/src/main/java/io/scanbot/example/MainActivity.kt
@@ -22,8 +22,8 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -51,11 +51,22 @@ class MainActivity : AppCompatActivity() {
             lifecycleScope.launch {
                 val dataExtractor = scanbotSdk.createDocumentDataExtractor().getOrThrow()
 
-            val result = withContext(Dispatchers.Default) {
-                val inputStream = contentResolver.openInputStream(uri) ?: throw IllegalStateException("Cannot open input stream from URI: $uri")
-                val imageRef = ImageRef.fromInputStream(inputStream)
-                dataExtractor.run(imageRef).getOrNull()
-            }
+                val imageRef = withContext(Dispatchers.IO) {
+                    contentResolver.openInputStream(uri)?.use { inputStream ->
+                        ImageRef.fromInputStream(inputStream)
+                    }
+                }
+                if (imageRef == null) {
+                    withContext(Dispatchers.Main) {
+                        showToast("Error opening selected image!")
+                        Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $uri")
+                    }
+                    return@launch
+                }
+
+                val result = withContext(Dispatchers.Default) {
+                    dataExtractor.run(imageRef).getOrNull()
+                }
 
                 withContext(Dispatchers.Main) {
                     DocumentsResultsStorage.result = result
diff --git a/classic-components-example/document-data-extractor-autosnapping/src/main/java/io/scanbot/example/ScannerActivity.kt b/classic-components-example/document-data-extractor-autosnapping/src/main/java/io/scanbot/example/ScannerActivity.kt
index 8d8d6399..d440f4b0 100644
--- a/classic-components-example/document-data-extractor-autosnapping/src/main/java/io/scanbot/example/ScannerActivity.kt
+++ b/classic-components-example/document-data-extractor-autosnapping/src/main/java/io/scanbot/example/ScannerActivity.kt
@@ -38,7 +38,7 @@ class ScannerActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_scanner)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(this.findViewById(R.id.root_view))
 
         scanbotSdk = ScanbotSDK(this)
diff --git a/classic-components-example/document-data-extractor-livedetection/build.gradle b/classic-components-example/document-data-extractor-livedetection/build.gradle
index d0bbb28f..a0966137 100644
--- a/classic-components-example/document-data-extractor-livedetection/build.gradle
+++ b/classic-components-example/document-data-extractor-livedetection/build.gradle
@@ -17,21 +17,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
     implementation("androidx.constraintlayout:constraintlayout:${project.ext.constraintLayoutVersion}")
diff --git a/classic-components-example/document-data-extractor-livedetection/proguard-rules.pro b/classic-components-example/document-data-extractor-livedetection/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/document-data-extractor-livedetection/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/document-data-extractor-livedetection/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/document-data-extractor-livedetection/src/main/java/io/scanbot/example/MainActivity.kt
index f792adc3..2305a525 100755
--- a/classic-components-example/document-data-extractor-livedetection/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/document-data-extractor-livedetection/src/main/java/io/scanbot/example/MainActivity.kt
@@ -10,8 +10,8 @@ import io.scanbot.example.common.showToast
 import io.scanbot.example.databinding.ActivityMainBinding
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
diff --git a/classic-components-example/document-data-extractor-livedetection/src/main/java/io/scanbot/example/ScannerActivity.kt b/classic-components-example/document-data-extractor-livedetection/src/main/java/io/scanbot/example/ScannerActivity.kt
index 25011a5c..1b5bc7fc 100644
--- a/classic-components-example/document-data-extractor-livedetection/src/main/java/io/scanbot/example/ScannerActivity.kt
+++ b/classic-components-example/document-data-extractor-livedetection/src/main/java/io/scanbot/example/ScannerActivity.kt
@@ -28,7 +28,7 @@ class ScannerActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_scanner)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(this.findViewById(R.id.root_view))
 
         cameraView = findViewById<ScanbotCameraXView>(R.id.cameraView)
diff --git a/classic-components-example/document-enhancer/build.gradle b/classic-components-example/document-enhancer/build.gradle
new file mode 100644
index 00000000..278714b4
--- /dev/null
+++ b/classic-components-example/document-enhancer/build.gradle
@@ -0,0 +1,46 @@
+plugins {
+    id("com.android.application")
+    id("org.jetbrains.kotlin.android")
+}
+
+android {
+    namespace = project.ext.submodulesNamespace
+    compileSdk = project.ext.compileSdkVersion
+
+    defaultConfig {
+        applicationId = project.ext.exampleAppId
+        minSdk = project.ext.minSdkVersion
+        targetSdk = project.ext.targetSdkVersion
+        versionCode = 1
+        versionName = "1.0"
+    }
+
+    buildTypes {
+        named("debug") {
+            
+            minifyEnabled = false
+            debuggable = true
+        }
+    }
+
+    packagingOptions {
+        exclude 'META-INF/LICENSE.txt'
+        exclude 'META-INF/LICENSE'
+        exclude 'META-INF/NOTICE.txt'
+        exclude 'META-INF/NOTICE'
+        exclude 'META-INF/DEPENDENCIES'
+    }
+
+    buildFeatures {
+        viewBinding = true
+    }
+}
+
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
+dependencies {
+    implementation(project(":common"))
+    implementation("io.scanbot:sdk-package-1:${project.ext.scanbotSdkVersion}")
+    implementation("io.scanbot:sdk-document-enhancer-assets:${project.ext.scanbotSdkVersion}")
+    implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
+}
diff --git a/classic-components-example/document-enhancer/src/main/AndroidManifest.xml b/classic-components-example/document-enhancer/src/main/AndroidManifest.xml
new file mode 100755
index 00000000..4d1192e4
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/AndroidManifest.xml
@@ -0,0 +1,31 @@
+<?xml version="1.0" encoding="utf-8"?>
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:tools="http://schemas.android.com/tools"
+    >
+
+    <uses-permission android:name="android.permission.CAMERA" />
+    <uses-permission android:name="android.permission.VIBRATE" />
+
+    <uses-feature android:name="android.hardware.camera" />
+
+    <application
+        android:name=".ExampleApplication"
+        android:allowBackup="true"
+        android:label="@string/app_name"
+        android:theme="@style/AppTheme"
+        tools:replace="android:theme">
+        <activity android:name=".DocumentCameraActivity" />
+        <activity
+            android:name=".MainActivity"
+            android:label="@string/app_name"
+            android:exported="true">
+            <intent-filter>
+                <action android:name="android.intent.action.MAIN" />
+
+                <category android:name="android.intent.category.LAUNCHER" />
+            </intent-filter>
+        </activity>
+
+    </application>
+
+</manifest>
diff --git a/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/DocumentCameraActivity.kt b/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/DocumentCameraActivity.kt
new file mode 100755
index 00000000..bd247620
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/DocumentCameraActivity.kt
@@ -0,0 +1,172 @@
+package io.scanbot.example
+
+
+import android.Manifest
+import android.content.pm.PackageManager
+import android.graphics.Color
+import android.os.Bundle
+import android.view.View
+import android.widget.Button
+import android.widget.ImageView
+import androidx.appcompat.app.AppCompatActivity
+import androidx.core.app.ActivityCompat
+import androidx.core.content.ContextCompat
+import androidx.core.view.WindowCompat
+import io.scanbot.common.onSuccess
+import io.scanbot.example.common.applyEdgeToEdge
+import io.scanbot.sdk.ScanbotSDK
+import io.scanbot.sdk.camera.CaptureInfo
+import io.scanbot.sdk.document.ui.DocumentScannerView
+import io.scanbot.sdk.document.ui.IDocumentScannerViewCallback
+import io.scanbot.sdk.documentscanner.DocumentEnhancer
+import io.scanbot.sdk.documentscanner.DocumentStraighteningMode
+import io.scanbot.sdk.documentscanner.DocumentStraighteningParameters
+import io.scanbot.sdk.image.ImageRef
+import io.scanbot.sdk.ui.camera.ShutterButton
+
+class DocumentCameraActivity : AppCompatActivity() {
+
+    private var flashEnabled = false
+    private var autoSnappingEnabled = true
+    private val ignoreOrientationMistmatch = true
+
+    private lateinit var documentScannerView: DocumentScannerView
+
+    private lateinit var resultView: ImageView
+    private lateinit var autoSnappingToggleButton: Button
+    private lateinit var shutterButton: ShutterButton
+
+
+    override fun onCreate(savedInstanceState: Bundle?) {
+        supportRequestWindowFeature(WindowCompat.FEATURE_ACTION_BAR_OVERLAY)
+
+        super.onCreate(savedInstanceState)
+        setContentView(R.layout.activity_camera)
+        askPermission()
+        supportActionBar!!.hide()
+        applyEdgeToEdge(findViewById(R.id.root_view))
+
+        val scanbotSdk = ScanbotSDK(this)
+
+        documentScannerView = findViewById(R.id.document_scanner_view)
+        resultView = findViewById<View>(R.id.result) as ImageView
+        val documentEnhancer = scanbotSdk.createDocumentEnhancer()
+        scanbotSdk.createDocumentScanner().onSuccess { documentScanner ->
+
+            documentScannerView.apply {
+                initCamera()
+                initScanningBehavior(
+                    documentScanner,
+                    { result, frame ->
+                        // Here you are continuously notified about document scanning results.
+                        // For example, you can show a user guidance text depending on the current scanning status.
+                        result.onSuccess { data ->
+                        }
+                        false // typically you need to return false
+                    },
+                    object : IDocumentScannerViewCallback {
+                        override fun onCameraOpen() {
+                            documentScannerView.viewController.useFlash(flashEnabled)
+                        }
+
+                        override fun onPictureTaken(image: ImageRef, captureInfo: CaptureInfo) {
+                            documentEnhancer.onSuccess { documentEnhancer ->
+                                processPictureTaken(image, documentEnhancer)
+                            }
+
+
+                            // continue scanning
+                            documentScannerView.postDelayed({
+                                documentScannerView.viewController.startPreview()
+                            }, 1000)
+                        }
+                    }
+                )
+            }
+        }
+
+        documentScannerView.polygonConfiguration.apply {
+            setPolygonFillColor(POLYGON_FILL_COLOR)
+            setPolygonFillColorOK(POLYGON_FILL_COLOR_OK)
+        }
+
+        documentScannerView.viewController.apply {
+            setAcceptedAngleScore(60.0)
+            setAcceptedSizeScore(75.0)
+            setIgnoreOrientationMismatch(ignoreOrientationMistmatch)
+
+            // Please note: https://docs.scanbot.io/document-scanner-sdk/android/features/document-scanner/autosnapping/#sensitivity
+            setAutoSnappingSensitivity(0.85f)
+        }
+
+        shutterButton = findViewById(R.id.shutterButton)
+        shutterButton.setOnClickListener { documentScannerView.viewController.takePicture(false) }
+        shutterButton.visibility = View.VISIBLE
+
+        findViewById<View>(R.id.flashToggle).setOnClickListener {
+            flashEnabled = !flashEnabled
+            documentScannerView.viewController.useFlash(flashEnabled)
+        }
+
+        autoSnappingToggleButton = findViewById(R.id.autoSnappingToggle)
+        autoSnappingToggleButton.setOnClickListener {
+            autoSnappingEnabled = !autoSnappingEnabled
+            setAutoSnapEnabled(autoSnappingEnabled)
+        }
+        autoSnappingToggleButton.post { setAutoSnapEnabled(autoSnappingEnabled) }
+    }
+
+    private fun askPermission() {
+        if (ContextCompat.checkSelfPermission(
+                this,
+                Manifest.permission.CAMERA
+            ) != PackageManager.PERMISSION_GRANTED
+        ) {
+            ActivityCompat.requestPermissions(this, arrayOf(Manifest.permission.CAMERA), 999)
+        }
+    }
+
+    override fun onResume() {
+        super.onResume()
+    }
+
+    override fun onPause() {
+        super.onPause()
+    }
+
+    private fun processPictureTaken(image: ImageRef, documentEnhancer: DocumentEnhancer) {
+        // STRAIGHTEN SCANNED IMAGE ASSUMING DOCUMENT IS BENT
+        // Run document enhancer unwarping on original image:
+        val result = documentEnhancer.straighten(image, DocumentStraighteningParameters().apply {
+            straighteningMode = DocumentStraighteningMode.STRAIGHTEN
+            // uncomment if you want wo set specific aspect ratios for documents
+            // aspectRatios = listOf(AspectRatio(29.0, 21.0))
+        }).getOrNull()
+
+        resultView.post {
+            resultView.setImageBitmap(
+                result?.straightenedImage?.toBitmap()?.getOrNull()
+            )
+        }
+    }
+
+    private fun setAutoSnapEnabled(enabled: Boolean) {
+        documentScannerView.viewController.apply {
+            autoSnappingEnabled = enabled
+            isFrameProcessingEnabled = enabled
+        }
+        documentScannerView.polygonConfiguration.setPolygonViewVisible(enabled)
+
+        autoSnappingToggleButton.text = "Automatic ${if (enabled) "ON" else "OFF"}"
+        if (enabled) {
+            shutterButton.showAutoButton()
+        } else {
+            shutterButton.showManualButton()
+        }
+    }
+
+    companion object {
+        private val POLYGON_FILL_COLOR = Color.parseColor("#55ff0000")
+        private val POLYGON_FILL_COLOR_OK = Color.parseColor("#4400ff00")
+    }
+}
diff --git a/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/ExampleApplication.kt b/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/ExampleApplication.kt
new file mode 100755
index 00000000..d366bec5
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/ExampleApplication.kt
@@ -0,0 +1,55 @@
+package io.scanbot.example
+
+import android.app.Application
+import io.scanbot.sdk.ScanbotSDK
+import io.scanbot.sdk.ScanbotSDKInitializer
+import io.scanbot.sdk.util.log.LoggerProvider
+import kotlinx.coroutines.CoroutineScope
+import kotlinx.coroutines.Dispatchers
+import kotlinx.coroutines.Job
+import kotlinx.coroutines.launch
+import kotlin.coroutines.CoroutineContext
+
+class ExampleApplication : Application(), CoroutineScope {
+
+    private var job: Job = Job()
+    override val coroutineContext: CoroutineContext
+        get() = Dispatchers.IO + job
+
+    /*
+     * TODO 1/2: Add the Scanbot SDK license key here.
+     * Please note: The Scanbot SDK will run without a license key for one minute per session!
+     * After the trial period is over all Scanbot SDK functions as well as the UI components will stop working.
+     * You can get an unrestricted "no-strings-attached" 30 day trial license key for free.
+     * Please submit the trial license form (https://scanbot.io/trial/) on our website by using
+     * the app identifier "io.scanbot.example.sdk.android" of this example app.
+     */
+    val licenseKey = ""
+
+    override fun onCreate() {
+        super.onCreate()
+
+        ScanbotSDKInitializer()
+            .withLogging(true)
+            // TODO 2/2: Enable the Scanbot SDK license key
+            //.license(this, licenseKey)
+            .licenseErrorHandler { status, feature, statusMessage ->
+                LoggerProvider.logger.d("ExampleApplication", "+++> License status: ${status.name}. Status message: $statusMessage")
+                LoggerProvider.logger.d("ExampleApplication", "+++> Feature not available: ${feature.name}")
+            }
+            //.sdkFilesDirectory(this, getExternalFilesDir(null)!!)
+            .initialize(this)
+
+        LoggerProvider.logger.d("ExampleApplication", "Scanbot SDK was initialized")
+
+        val licenseInfo = ScanbotSDK(this).licenseInfo
+        LoggerProvider.logger.d("ExampleApplication", "License status: ${licenseInfo.status}")
+        LoggerProvider.logger.d("ExampleApplication", "License isValid: ${licenseInfo.isValid}")
+        LoggerProvider.logger.d("ExampleApplication", "License expirationDate: ${licenseInfo.expirationDateString}")
+
+        launch {
+            // Clear all previously created documents in storage
+            ScanbotSDK(this@ExampleApplication).documentApi.deleteAllDocuments()
+        }
+    }
+}
diff --git a/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/MainActivity.kt
new file mode 100644
index 00000000..7f75a3d2
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/java/io/scanbot/example/MainActivity.kt
@@ -0,0 +1,113 @@
+package io.scanbot.example
+
+import android.Manifest
+import android.content.Intent
+import android.net.Uri
+import android.os.Bundle
+import android.util.Log
+import android.view.View
+import androidx.activity.result.PickVisualMediaRequest
+import androidx.activity.result.contract.ActivityResultContracts
+import androidx.appcompat.app.AppCompatActivity
+import androidx.lifecycle.lifecycleScope
+import io.scanbot.common.onSuccess
+
+
+import io.scanbot.example.common.Const
+import io.scanbot.example.common.applyEdgeToEdge
+import io.scanbot.example.common.showToast
+import io.scanbot.example.databinding.ActivityMainBinding
+import io.scanbot.sdk.ScanbotSDK
+import io.scanbot.sdk.documentscanner.DocumentStraighteningMode
+import io.scanbot.sdk.documentscanner.DocumentStraighteningParameters
+import io.scanbot.sdk.image.ImageRef
+import io.scanbot.sdk.util.PolygonHelper
+import kotlinx.coroutines.Dispatchers
+import kotlinx.coroutines.launch
+import kotlinx.coroutines.withContext
+
+/**
+Ths example uses new SDK APIs presented in Scanbot SDK v.8.x.x
+Please, check the official documentation for more details:
+Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
+ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
+ */
+
+class MainActivity : AppCompatActivity() {
+
+    private val scanbotSdk: ScanbotSDK by lazy { ScanbotSDK(this) }
+
+    private val binding by lazy { ActivityMainBinding.inflate(layoutInflater) }
+
+    private val requestCameraLauncher =
+        registerForActivityResult(ActivityResultContracts.RequestPermission()) { isGranted ->
+            if (isGranted) {
+                startActivity(Intent(this, DocumentCameraActivity::class.java))
+            } else {
+                this@MainActivity.showToast("Camera permission is required to run this example!")
+            }
+        }
+
+    private val selectGalleryImageResultLauncher =
+        registerForActivityResult(ActivityResultContracts.PickVisualMedia()) { uri ->
+            if (!scanbotSdk.licenseInfo.isValid) {
+                this@MainActivity.showToast("1-minute trial license has expired!")
+                Log.e(Const.LOG_TAG, "1-minute trial license has expired!")
+                return@registerForActivityResult
+            }
+
+            if (uri == null) {
+                showToast("Error obtaining selected image!")
+                Log.e(Const.LOG_TAG, "Error obtaining selected image!")
+                return@registerForActivityResult
+            }
+
+            lifecycleScope.launch { processImage(uri) }
+        }
+
+    override fun onCreate(savedInstanceState: Bundle?) {
+        super.onCreate(savedInstanceState)
+        setContentView(binding.root)
+        supportActionBar?.hide()
+        applyEdgeToEdge(findViewById(R.id.root_view))
+
+        binding.showDocScannerBtn.setOnClickListener {
+            requestCameraLauncher.launch(Manifest.permission.CAMERA)
+        }
+
+        binding.importImage.setOnClickListener {
+            selectGalleryImageResultLauncher.launch(PickVisualMediaRequest(ActivityResultContracts.PickVisualMedia.ImageOnly))
+        }
+    }
+
+    /** Imports a selected image and performs document straightening on it. */
+    private suspend fun processImage(uri: Uri) {
+        withContext(Dispatchers.Main) {
+            binding.progressBar.visibility = View.VISIBLE
+            this@MainActivity.showToast("Importing page...")
+        }
+
+        val documentImage = withContext(Dispatchers.Default) {
+            // load the selected image
+            val image = contentResolver.openInputStream(uri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
+            } ?: throw IllegalStateException("Cannot open input stream from URI: $uri")
+
+            // run document scanning on the image:
+            scanbotSdk.createDocumentEnhancer().getOrNull()
+                ?.straighten(image, parameters = DocumentStraighteningParameters().apply {
+                    straighteningMode = DocumentStraighteningMode.STRAIGHTEN
+                    // uncomment if you want wo set specific aspect ratios for documents
+                    // aspectRatios = listOf(AspectRatio(29.0, 21.0))
+                })?.getOrNull()?.straightenedImage?.toBitmap()?.getOrNull()
+        }
+
+        withContext(Dispatchers.Main) {
+            binding.progressBar.visibility = View.GONE
+
+            // present straightened image:
+            binding.importResultImage.setImageBitmap(documentImage)
+            binding.importResultImage.visibility = View.VISIBLE
+        }
+    }
+}
diff --git a/classic-components-example/document-enhancer/src/main/res/layout/activity_camera.xml b/classic-components-example/document-enhancer/src/main/res/layout/activity_camera.xml
new file mode 100755
index 00000000..f059f4db
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/res/layout/activity_camera.xml
@@ -0,0 +1,43 @@
+<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:app="http://schemas.android.com/apk/res-auto"
+    xmlns:tools="http://schemas.android.com/tools"
+    android:id="@+id/root_view"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+    tools:context=".DocumentCameraActivity">
+
+    <io.scanbot.sdk.document.ui.DocumentScannerView
+        android:id="@+id/document_scanner_view"
+        android:layout_width="match_parent"
+        android:layout_height="match_parent" />
+
+    <Button
+        android:id="@+id/flashToggle"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_gravity="top|end"
+        android:text="Flash" />
+
+    <Button
+        android:id="@+id/autoSnappingToggle"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_gravity="top|start"
+        android:text="Automatic" />
+
+    <ImageView
+        android:id="@+id/result"
+        android:layout_width="100dp"
+        android:layout_height="100dp"
+        android:layout_gravity="bottom|end"
+        android:layout_marginBottom="15dp" />
+
+    <io.scanbot.sdk.ui.camera.ShutterButton
+        android:id="@+id/shutterButton"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_gravity="bottom|center_horizontal"
+        android:layout_marginBottom="15dp"
+        android:elevation="6dp" />
+
+</FrameLayout>
diff --git a/classic-components-example/document-enhancer/src/main/res/layout/activity_main.xml b/classic-components-example/document-enhancer/src/main/res/layout/activity_main.xml
new file mode 100755
index 00000000..638005e1
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/res/layout/activity_main.xml
@@ -0,0 +1,45 @@
+<?xml version="1.0" encoding="utf-8"?>
+<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:tools="http://schemas.android.com/tools"
+    android:id="@+id/root_view"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+    android:paddingStart="@dimen/activity_horizontal_margin"
+    android:paddingTop="@dimen/activity_vertical_margin"
+    android:paddingEnd="@dimen/activity_horizontal_margin"
+    android:paddingBottom="@dimen/activity_vertical_margin"
+    tools:context="io.scanbot.example.MainActivity">
+
+    <androidx.appcompat.widget.LinearLayoutCompat
+        android:layout_width="match_parent"
+        android:layout_height="match_parent"
+        android:gravity="center_horizontal"
+        android:orientation="vertical"
+        tools:context="io.scanbot.example.MainActivity">
+
+        <Button
+            android:id="@+id/show_doc_scanner_btn"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:text="Scan document and enhance" />
+
+        <Button
+            android:id="@+id/import_image"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:text="Import image and enhance" />
+    </androidx.appcompat.widget.LinearLayoutCompat>
+
+    <ProgressBar
+        android:id="@+id/progress_bar"
+        android:layout_width="50dp"
+        android:layout_height="50dp"
+        android:layout_gravity="center"
+        android:visibility="gone" />
+
+    <ImageView
+        android:id="@+id/import_result_image"
+        android:layout_width="150dp"
+        android:layout_height="150dp"
+        android:layout_gravity="bottom|end" />
+</FrameLayout>
diff --git a/classic-components-example/document-enhancer/src/main/res/menu/menu_main.xml b/classic-components-example/document-enhancer/src/main/res/menu/menu_main.xml
new file mode 100755
index 00000000..8847389d
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/res/menu/menu_main.xml
@@ -0,0 +1,6 @@
+<menu xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:app="http://schemas.android.com/apk/res-auto"
+    xmlns:tools="http://schemas.android.com/tools" tools:context=".DocumentCameraActivity">
+    <item android:id="@+id/action_settings" android:title="@string/action_settings"
+        android:orderInCategory="100" app:showAsAction="never" />
+</menu>
diff --git a/classic-components-example/document-enhancer/src/main/res/mipmap-hdpi/icon.png b/classic-components-example/document-enhancer/src/main/res/mipmap-hdpi/icon.png
new file mode 100755
index 00000000..cde69bcc
Binary files /dev/null and b/classic-components-example/document-enhancer/src/main/res/mipmap-hdpi/icon.png differ
diff --git a/classic-components-example/document-enhancer/src/main/res/mipmap-mdpi/icon.png b/classic-components-example/document-enhancer/src/main/res/mipmap-mdpi/icon.png
new file mode 100755
index 00000000..c133a0cb
Binary files /dev/null and b/classic-components-example/document-enhancer/src/main/res/mipmap-mdpi/icon.png differ
diff --git a/classic-components-example/document-enhancer/src/main/res/mipmap-xhdpi/icon.png b/classic-components-example/document-enhancer/src/main/res/mipmap-xhdpi/icon.png
new file mode 100755
index 00000000..bfa42f0e
Binary files /dev/null and b/classic-components-example/document-enhancer/src/main/res/mipmap-xhdpi/icon.png differ
diff --git a/classic-components-example/document-enhancer/src/main/res/mipmap-xxhdpi/icon.png b/classic-components-example/document-enhancer/src/main/res/mipmap-xxhdpi/icon.png
new file mode 100755
index 00000000..324e72cd
Binary files /dev/null and b/classic-components-example/document-enhancer/src/main/res/mipmap-xxhdpi/icon.png differ
diff --git a/classic-components-example/document-enhancer/src/main/res/values-w820dp/dimens.xml b/classic-components-example/document-enhancer/src/main/res/values-w820dp/dimens.xml
new file mode 100755
index 00000000..63fc8164
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/res/values-w820dp/dimens.xml
@@ -0,0 +1,6 @@
+<resources>
+    <!-- Example customization of dimensions originally defined in res/values/dimens.xml
+         (such as screen margins) for screens with more than 820dp of available width. This
+         would include 7" and 10" devices in landscape (~960dp and ~1280dp respectively). -->
+    <dimen name="activity_horizontal_margin">64dp</dimen>
+</resources>
diff --git a/classic-components-example/document-enhancer/src/main/res/values/dimens.xml b/classic-components-example/document-enhancer/src/main/res/values/dimens.xml
new file mode 100755
index 00000000..47c82246
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/res/values/dimens.xml
@@ -0,0 +1,5 @@
+<resources>
+    <!-- Default screen margins, per the Android Design guidelines. -->
+    <dimen name="activity_horizontal_margin">16dp</dimen>
+    <dimen name="activity_vertical_margin">16dp</dimen>
+</resources>
diff --git a/classic-components-example/document-enhancer/src/main/res/values/strings.xml b/classic-components-example/document-enhancer/src/main/res/values/strings.xml
new file mode 100755
index 00000000..cce69b24
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/res/values/strings.xml
@@ -0,0 +1,6 @@
+<resources>
+    <string name="app_name">Scanbot SDK Example</string>
+
+
+    <string name="action_settings">Settings</string>
+</resources>
diff --git a/classic-components-example/document-enhancer/src/main/res/values/styles.xml b/classic-components-example/document-enhancer/src/main/res/values/styles.xml
new file mode 100755
index 00000000..766ab993
--- /dev/null
+++ b/classic-components-example/document-enhancer/src/main/res/values/styles.xml
@@ -0,0 +1,8 @@
+<resources>
+
+    <!-- Base application theme. -->
+    <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
+        <!-- Customize your theme here. -->
+    </style>
+
+</resources>
diff --git a/classic-components-example/document-quality-analyzer/build.gradle b/classic-components-example/document-quality-analyzer/build.gradle
index 8f49c0f1..66e4b22e 100755
--- a/classic-components-example/document-quality-analyzer/build.gradle
+++ b/classic-components-example/document-quality-analyzer/build.gradle
@@ -15,21 +15,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/document-quality-analyzer/proguard-rules.pro b/classic-components-example/document-quality-analyzer/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/document-quality-analyzer/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/document-quality-analyzer/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/document-quality-analyzer/src/main/java/io/scanbot/example/MainActivity.kt
index dab4b065..33775076 100755
--- a/classic-components-example/document-quality-analyzer/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/document-quality-analyzer/src/main/java/io/scanbot/example/MainActivity.kt
@@ -19,8 +19,8 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -55,7 +55,7 @@ class MainActivity : AppCompatActivity() {
         supportRequestWindowFeature(WindowCompat.FEATURE_ACTION_BAR_OVERLAY)
         super.onCreate(savedInstanceState)
         setContentView(binding.root)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         binding.galleryButton.setOnClickListener {
@@ -72,11 +72,17 @@ class MainActivity : AppCompatActivity() {
 
     private suspend fun estimateOnStillImage(imageUri: Uri) {
         val image = withContext(Dispatchers.IO) {
-            contentResolver.openInputStream(imageUri).use { inputStream ->
-                inputStream?.let { ImageRef.fromInputStream(it) }
+            contentResolver.openInputStream(imageUri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
             }
         }
-        if (image == null) return
+        if (image == null) {
+            withContext(Dispatchers.Main) {
+                showToast("Error opening selected image!")
+                Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $imageUri")
+            }
+            return
+        }
         withContext(Dispatchers.Main) {
             binding.stillImageImageView.setImageBitmap(image?.toBitmap()?.getOrNull())
         }
diff --git a/classic-components-example/document-scanner/build.gradle b/classic-components-example/document-scanner/build.gradle
index c3414bb5..aa5fad96 100644
--- a/classic-components-example/document-scanner/build.gradle
+++ b/classic-components-example/document-scanner/build.gradle
@@ -17,16 +17,12 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     packagingOptions {
         exclude 'META-INF/LICENSE.txt'
         exclude 'META-INF/LICENSE'
@@ -40,6 +36,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("io.scanbot:sdk-package-1:${project.ext.scanbotSdkVersion}")
diff --git a/classic-components-example/document-scanner/src/main/java/io/scanbot/example/DocumentCameraActivity.kt b/classic-components-example/document-scanner/src/main/java/io/scanbot/example/DocumentCameraActivity.kt
index 266e13c0..31046ea3 100755
--- a/classic-components-example/document-scanner/src/main/java/io/scanbot/example/DocumentCameraActivity.kt
+++ b/classic-components-example/document-scanner/src/main/java/io/scanbot/example/DocumentCameraActivity.kt
@@ -36,7 +36,7 @@ class DocumentCameraActivity : AppCompatActivity() {
     private var lastUserGuidanceHintTs = 0L
     private var flashEnabled = false
     private var autoSnappingEnabled = true
-    private val ignoreOrientationMistmatch = true
+    private val ignoreOrientationMismatch = true
 
     private lateinit var documentScannerView: DocumentScannerView
 
@@ -52,7 +52,7 @@ class DocumentCameraActivity : AppCompatActivity() {
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_camera)
         askPermission()
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         val scanbotSdk = ScanbotSDK(this)
@@ -116,7 +116,7 @@ class DocumentCameraActivity : AppCompatActivity() {
         documentScannerView.viewController.apply {
             setAcceptedAngleScore(60.0)
             setAcceptedSizeScore(75.0)
-            setIgnoreOrientationMismatch(ignoreOrientationMistmatch)
+            setIgnoreOrientationMismatch(ignoreOrientationMismatch)
 
             // Please note: https://docs.scanbot.io/document-scanner-sdk/android/features/document-scanner/autosnapping/#sensitivity
             setAutoSnappingSensitivity(0.85f)
@@ -151,16 +151,6 @@ class DocumentCameraActivity : AppCompatActivity() {
         }
     }
 
-    override fun onResume() {
-        super.onResume()
-        documentScannerView.viewController.onResume()
-    }
-
-    override fun onPause() {
-        super.onPause()
-        documentScannerView.viewController.onPause()
-    }
-
     private fun showUserGuidance(result: DocumentDetectionStatus) {
         if (!autoSnappingEnabled) {
             return
@@ -196,7 +186,7 @@ class DocumentCameraActivity : AppCompatActivity() {
             }
 
             DocumentDetectionStatus.OK_BUT_BAD_ASPECT_RATIO -> {
-                if (ignoreOrientationMistmatch) {
+                if (ignoreOrientationMismatch) {
                     userGuidanceHint.text = "Don't move"
                 } else {
                     userGuidanceHint.text = "Wrong aspect ratio.\nRotate your device."
diff --git a/classic-components-example/document-scanner/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/document-scanner/src/main/java/io/scanbot/example/MainActivity.kt
index 047a0795..3c14c76e 100644
--- a/classic-components-example/document-scanner/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/document-scanner/src/main/java/io/scanbot/example/MainActivity.kt
@@ -11,8 +11,6 @@ import androidx.activity.result.contract.ActivityResultContracts
 import androidx.appcompat.app.AppCompatActivity
 import androidx.lifecycle.lifecycleScope
 import io.scanbot.common.onSuccess
-
-
 import io.scanbot.example.common.Const
 import io.scanbot.example.common.applyEdgeToEdge
 import io.scanbot.example.common.showToast
@@ -25,10 +23,10 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
-Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
-ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
+ * This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+ * Please check the official documentation for more details:
+ * Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
+ * ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
 
 class MainActivity : AppCompatActivity() {
@@ -91,7 +89,6 @@ class MainActivity : AppCompatActivity() {
                 ImageRef.fromInputStream(inputStream)
             } ?: throw IllegalStateException("Cannot open input stream from URI: $uri")
 
-
             // create a new Page object with given image as original image:
             val document = scanbotSdk.documentApi.createDocument()
                 .getOrNull() //can be handled with .getOrThrow() if needed
diff --git a/classic-components-example/document-scanner/src/main/res/values/strings.xml b/classic-components-example/document-scanner/src/main/res/values/strings.xml
index 21db9902..cce69b24 100755
--- a/classic-components-example/document-scanner/src/main/res/values/strings.xml
+++ b/classic-components-example/document-scanner/src/main/res/values/strings.xml
@@ -1,6 +1,6 @@
 <resources>
     <string name="app_name">Scanbot SDK Example</string>
 
-    <string name="hello_world">Hello world!</string>
+
     <string name="action_settings">Settings</string>
 </resources>
diff --git a/classic-components-example/edit-polygon-view/build.gradle b/classic-components-example/edit-polygon-view/build.gradle
index df9d49d7..baab0b54 100644
--- a/classic-components-example/edit-polygon-view/build.gradle
+++ b/classic-components-example/edit-polygon-view/build.gradle
@@ -17,16 +17,12 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     packagingOptions {
         exclude 'META-INF/LICENSE.txt'
         exclude 'META-INF/LICENSE'
@@ -40,6 +36,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation fileTree(include: ['*.jar'], dir: 'libs')
     implementation(project(":common"))
diff --git a/classic-components-example/edit-polygon-view/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/edit-polygon-view/src/main/java/io/scanbot/example/MainActivity.kt
index 9d46ed9c..62cc365a 100755
--- a/classic-components-example/edit-polygon-view/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/edit-polygon-view/src/main/java/io/scanbot/example/MainActivity.kt
@@ -24,8 +24,8 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -58,7 +58,7 @@ class MainActivity : AppCompatActivity() {
 
         scanner = scanbotSDK.createDocumentScanner().getOrThrow()
 
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
 
         editPolygonView = findViewById(R.id.polygonView)
         magnifierView = findViewById(R.id.magnifier)
diff --git a/classic-components-example/encryption/build.gradle b/classic-components-example/encryption/build.gradle
index cbc3a076..4e5720a1 100644
--- a/classic-components-example/encryption/build.gradle
+++ b/classic-components-example/encryption/build.gradle
@@ -15,21 +15,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/gradle/wrapper/gradle-wrapper.properties b/classic-components-example/gradle/wrapper/gradle-wrapper.properties
index c6e558f1..f47aaeb1 100755
--- a/classic-components-example/gradle/wrapper/gradle-wrapper.properties
+++ b/classic-components-example/gradle/wrapper/gradle-wrapper.properties
@@ -3,4 +3,4 @@ distributionBase=GRADLE_USER_HOME
 distributionPath=wrapper/dists
 zipStoreBase=GRADLE_USER_HOME
 zipStorePath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-8.5-bin.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-8.13-bin.zip
diff --git a/classic-components-example/manual-processing/build.gradle b/classic-components-example/manual-processing/build.gradle
index baf5c167..349e84f5 100644
--- a/classic-components-example/manual-processing/build.gradle
+++ b/classic-components-example/manual-processing/build.gradle
@@ -17,16 +17,12 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     packagingOptions {
         exclude 'META-INF/LICENSE.txt'
         exclude 'META-INF/LICENSE'
@@ -40,6 +36,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/manual-processing/proguard-rules.pro b/classic-components-example/manual-processing/proguard-rules.pro
deleted file mode 100644
index f1b42451..00000000
--- a/classic-components-example/manual-processing/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/manual-processing/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/manual-processing/src/main/java/io/scanbot/example/MainActivity.kt
index 3748b32b..f7c8b384 100755
--- a/classic-components-example/manual-processing/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/manual-processing/src/main/java/io/scanbot/example/MainActivity.kt
@@ -23,8 +23,8 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -66,10 +66,21 @@ class MainActivity : AppCompatActivity() {
     private suspend fun processImage(imageUri: Uri) {
         withContext(Dispatchers.Main) { binding.progressBar.visibility = View.VISIBLE }
 
+        val image = withContext(Dispatchers.IO) {
+            contentResolver.openInputStream(imageUri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
+            }
+        }
+        if (image == null) {
+            withContext(Dispatchers.Main) {
+                binding.progressBar.visibility = View.GONE
+                showToast("Error opening selected image!")
+                Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $imageUri")
+            }
+            return
+        }
+
         val page = withContext(Dispatchers.Default) {
-            val inputStream = contentResolver.openInputStream(imageUri)
-                ?: throw IllegalStateException("Cannot open input stream from URI: $imageUri")
-            val image = ImageRef.fromInputStream(inputStream)
             val scanner = scanbotSdk.createDocumentScanner().getOrThrow()
             val detectedPolygon =
                 scanner.run(image).getOrNull()?.pointsNormalized ?: PolygonHelper.getFullPolygon()
diff --git a/classic-components-example/manual-processing/src/main/res/values/strings.xml b/classic-components-example/manual-processing/src/main/res/values/strings.xml
index 21db9902..cce69b24 100755
--- a/classic-components-example/manual-processing/src/main/res/values/strings.xml
+++ b/classic-components-example/manual-processing/src/main/res/values/strings.xml
@@ -1,6 +1,6 @@
 <resources>
     <string name="app_name">Scanbot SDK Example</string>
 
-    <string name="hello_world">Hello world!</string>
+
     <string name="action_settings">Settings</string>
 </resources>
diff --git a/classic-components-example/mc-scanner/build.gradle b/classic-components-example/mc-scanner/build.gradle
index e7c7ae66..d9dfbfce 100644
--- a/classic-components-example/mc-scanner/build.gradle
+++ b/classic-components-example/mc-scanner/build.gradle
@@ -17,21 +17,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/mc-scanner/proguard-rules.pro b/classic-components-example/mc-scanner/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/mc-scanner/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/MainActivity.kt
index 9add4cac..06eac728 100755
--- a/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/MainActivity.kt
@@ -22,8 +22,8 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -56,11 +56,21 @@ class MainActivity : AppCompatActivity() {
             binding.progressBar.isVisible = true
         }
 
-        val result = withContext(Dispatchers.Default) {
-            val inputStream = contentResolver.openInputStream(uri)
-                ?: throw IllegalStateException("Cannot open input stream from URI: $uri")
-            val imageRef = ImageRef.fromInputStream(inputStream)
+        val imageRef = withContext(Dispatchers.IO) {
+            contentResolver.openInputStream(uri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
+            }
+        }
+        if (imageRef == null) {
+            withContext(Dispatchers.Main) {
+                binding.progressBar.isVisible = false
+                showToast("Error opening selected image!")
+                Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $uri")
+            }
+            return
+        }
 
+        val result = withContext(Dispatchers.Default) {
             val scanner = scanbotSdk.createMedicalCertificateScanner().getOrThrow()
 
             scanner.run(
diff --git a/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/ManualMedicalCertificateScannerActivity.kt b/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/ManualMedicalCertificateScannerActivity.kt
index b2e75d7b..f5ff95ff 100755
--- a/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/ManualMedicalCertificateScannerActivity.kt
+++ b/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/ManualMedicalCertificateScannerActivity.kt
@@ -42,7 +42,7 @@ class ManualMedicalCertificateScannerActivity : AppCompatActivity() {
         supportRequestWindowFeature(WindowCompat.FEATURE_ACTION_BAR_OVERLAY)
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_manual_mc_scanner)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         askPermission()
diff --git a/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/MedicalCertificateRecognizerActivity.kt b/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/MedicalCertificateRecognizerActivity.kt
index 77346fde..62524112 100755
--- a/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/MedicalCertificateRecognizerActivity.kt
+++ b/classic-components-example/mc-scanner/src/main/java/io/scanbot/example/MedicalCertificateRecognizerActivity.kt
@@ -44,7 +44,7 @@ class MedicalCertificateScannerActivity : AppCompatActivity() {
         supportRequestWindowFeature(WindowCompat.FEATURE_ACTION_BAR_OVERLAY)
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_mc_scanner)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
         askPermission()
         resultImageView = findViewById(R.id.resultImageView)
diff --git a/classic-components-example/mrz-scanner/build.gradle b/classic-components-example/mrz-scanner/build.gradle
index cc1f36a3..1f435305 100644
--- a/classic-components-example/mrz-scanner/build.gradle
+++ b/classic-components-example/mrz-scanner/build.gradle
@@ -17,21 +17,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/mrz-scanner/proguard-rules.pro b/classic-components-example/mrz-scanner/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/mrz-scanner/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MRZLiveScanningActivity.kt b/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MRZLiveScanningActivity.kt
index 78a5a5f9..6c10173b 100755
--- a/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MRZLiveScanningActivity.kt
+++ b/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MRZLiveScanningActivity.kt
@@ -36,7 +36,7 @@ class MRZLiveScanningActivity : AppCompatActivity() {
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_mrz_live_scanner)
         askPermission()
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         // Configure Initial camera state
diff --git a/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MRZStillImageDetectionActivity.kt b/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MRZStillImageDetectionActivity.kt
index 74c1b4b1..5245158c 100755
--- a/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MRZStillImageDetectionActivity.kt
+++ b/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MRZStillImageDetectionActivity.kt
@@ -66,7 +66,7 @@ class MrzStillImageScanningActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(binding.root)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         docScannerResultLauncher =
@@ -121,10 +121,21 @@ class MrzStillImageScanningActivity : AppCompatActivity() {
     }
 
     private suspend fun importImageToPage(uri: Uri) {
-        val page = withContext(Dispatchers.Default) {
-            val inputStream = contentResolver.openInputStream(uri) ?: throw IllegalStateException("Cannot open input stream from URI: $uri")
-            val image = ImageRef.fromInputStream(inputStream)
+        val image = withContext(Dispatchers.IO) {
+            contentResolver.openInputStream(uri)?.use { inputStream ->
+                ImageRef.fromInputStream(inputStream)
+            }
+        }
+        if (image == null) {
+            withContext(Dispatchers.Main) {
+                binding.progressBar.visibility = View.GONE
+                showToast("Error opening selected image!")
+                Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $uri")
+            }
+            return
+        }
 
+        val page = withContext(Dispatchers.Default) {
             val document = scanbotSdk.documentApi.createDocument().getOrThrow() // can be handled with .getOrNull() if needed
             val page = document.addPage(image).getOrThrow() // can be handled with .getOrNull() if needed
 
diff --git a/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MainActivity.kt
index 8d255df7..9aa64ea4 100755
--- a/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/mrz-scanner/src/main/java/io/scanbot/example/MainActivity.kt
@@ -8,8 +8,8 @@ import io.scanbot.example.common.applyEdgeToEdge
 import io.scanbot.example.databinding.ActivityMainBinding
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
diff --git a/classic-components-example/mrz-scanner/src/main/res/layout/activity_main.xml b/classic-components-example/mrz-scanner/src/main/res/layout/activity_main.xml
index c82a7bb8..3f720954 100755
--- a/classic-components-example/mrz-scanner/src/main/res/layout/activity_main.xml
+++ b/classic-components-example/mrz-scanner/src/main/res/layout/activity_main.xml
@@ -18,6 +18,7 @@
             app:layout_constraintEnd_toEndOf="parent"
             android:layout_marginStart="8dp"
             app:layout_constraintStart_toStartOf="parent"
+            app:layout_constraintTop_toTopOf="parent"
             app:layout_constraintHorizontal_bias="0.502" />
 
         <Button
@@ -27,10 +28,12 @@
             android:layout_marginTop="16dp"
             android:text="MRZ Still Image Scanning"
             app:layout_constraintTop_toBottomOf="@+id/live_scanner_btn"
+            app:layout_constraintBottom_toBottomOf="parent"
             android:layout_marginEnd="8dp"
             app:layout_constraintEnd_toEndOf="parent"
             android:layout_marginStart="8dp"
             app:layout_constraintStart_toStartOf="parent"
-            app:layout_constraintHorizontal_bias="0.502" />
+            app:layout_constraintHorizontal_bias="0.502"
+            app:layout_constraintVertical_bias="0.0" />
 
 </androidx.constraintlayout.widget.ConstraintLayout>
diff --git a/classic-components-example/ocr/build.gradle b/classic-components-example/ocr/build.gradle
index 1222c43f..31511bb8 100644
--- a/classic-components-example/ocr/build.gradle
+++ b/classic-components-example/ocr/build.gradle
@@ -17,7 +17,7 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
@@ -31,15 +31,13 @@ android {
         exclude 'META-INF/DEPENDENCIES'
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/ocr/proguard-rules.pro b/classic-components-example/ocr/proguard-rules.pro
deleted file mode 100755
index a988b426..00000000
--- a/classic-components-example/ocr/proguard-rules.pro
+++ /dev/null
@@ -1,17 +0,0 @@
-# Add project specific ProGuard rules here.
-# By default, the flags in this file are appended to flags specified
-# in /Users/artem.kubiria/Development/sdk/tools/proguard/proguard-android.txt
-# You can edit the include path and order by changing the proguardFiles
-# directive in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# Add any project specific keep options here:
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
diff --git a/classic-components-example/ocr/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/ocr/src/main/java/io/scanbot/example/MainActivity.kt
index 9f81b2f1..992f5357 100755
--- a/classic-components-example/ocr/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/ocr/src/main/java/io/scanbot/example/MainActivity.kt
@@ -24,8 +24,8 @@ import kotlinx.coroutines.runBlocking
 import kotlinx.coroutines.withContext
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -62,7 +62,7 @@ class MainActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(binding.root)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         binding.scanButton.setOnClickListener {
diff --git a/classic-components-example/ocr/src/main/res/menu/menu_main.xml b/classic-components-example/ocr/src/main/res/menu/menu_main.xml
index 87a750ec..5a39ac87 100755
--- a/classic-components-example/ocr/src/main/res/menu/menu_main.xml
+++ b/classic-components-example/ocr/src/main/res/menu/menu_main.xml
@@ -1,5 +1,7 @@
 <menu xmlns:android="http://schemas.android.com/apk/res/android"
-    xmlns:tools="http://schemas.android.com/tools" tools:context=".MainActivity">
+    xmlns:app="http://schemas.android.com/apk/res-auto"
+    xmlns:tools="http://schemas.android.com/tools"
+    tools:context=".MainActivity">
     <item android:id="@+id/action_settings" android:title="@string/action_settings"
-        android:orderInCategory="100" android:showAsAction="never" />
+        android:orderInCategory="100" app:showAsAction="never" />
 </menu>
diff --git a/classic-components-example/ocr/src/main/res/values/strings.xml b/classic-components-example/ocr/src/main/res/values/strings.xml
index 21db9902..cce69b24 100755
--- a/classic-components-example/ocr/src/main/res/values/strings.xml
+++ b/classic-components-example/ocr/src/main/res/values/strings.xml
@@ -1,6 +1,6 @@
 <resources>
     <string name="app_name">Scanbot SDK Example</string>
 
-    <string name="hello_world">Hello world!</string>
+
     <string name="action_settings">Settings</string>
 </resources>
diff --git a/classic-components-example/pdf-generation/build.gradle b/classic-components-example/pdf-generation/build.gradle
index 763eab52..5a2246fc 100644
--- a/classic-components-example/pdf-generation/build.gradle
+++ b/classic-components-example/pdf-generation/build.gradle
@@ -17,7 +17,7 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
diff --git a/classic-components-example/pdf-generation/proguard-rules.pro b/classic-components-example/pdf-generation/proguard-rules.pro
deleted file mode 100755
index fef135a6..00000000
--- a/classic-components-example/pdf-generation/proguard-rules.pro
+++ /dev/null
@@ -1,17 +0,0 @@
-# Add project specific ProGuard rules here.
-# By default, the flags in this file are appended to flags specified
-# in /Users/doo/sdk/tools/proguard/proguard-android.txt
-# You can edit the include path and order by changing the proguardFiles
-# directive in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# Add any project specific keep options here:
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
diff --git a/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/MainActivity.kt
index 5da20194..40e9ca0c 100755
--- a/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/MainActivity.kt
@@ -12,7 +12,7 @@ class MainActivity : AppCompatActivity() {
         super.onCreate(savedInstanceState)
         val binding = ActivityMainBinding.inflate(layoutInflater)
         setContentView(binding.root)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(binding.root)
 
         binding.pdfButton.setOnClickListener {
diff --git a/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/PdfActivity.kt b/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/PdfActivity.kt
index e78c8b04..bb7f605c 100644
--- a/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/PdfActivity.kt
+++ b/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/PdfActivity.kt
@@ -33,7 +33,7 @@ import java.io.File
 
 /** This example uses new sdk APIs presented in Scanbot SDK v.8.x.x
  *
- * Please, check the official documentation for more details:
+ * Please check the official documentation for more details:
  * Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
  * ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -67,7 +67,7 @@ class PdfActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(binding.root)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         binding.scanButton.setOnClickListener {
diff --git a/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/PdfWithOcrActivity.kt b/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/PdfWithOcrActivity.kt
index eb59f928..cd192cc9 100644
--- a/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/PdfWithOcrActivity.kt
+++ b/classic-components-example/pdf-generation/src/main/java/io/scanbot/example/PdfWithOcrActivity.kt
@@ -34,7 +34,7 @@ import java.io.File
 
 /** This example uses new sdk APIs presented in Scanbot SDK v.8.x.x
  *
- * Please, check the official documentation for more details:
+ * Please check the official documentation for more details:
  * Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
  * ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -68,7 +68,7 @@ class PdfWithOcrActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(binding.root)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(binding.root)
 
         binding.scanButton.setOnClickListener {
diff --git a/classic-components-example/pdf-generation/src/main/res/values/strings.xml b/classic-components-example/pdf-generation/src/main/res/values/strings.xml
index 21db9902..cce69b24 100755
--- a/classic-components-example/pdf-generation/src/main/res/values/strings.xml
+++ b/classic-components-example/pdf-generation/src/main/res/values/strings.xml
@@ -1,6 +1,6 @@
 <resources>
     <string name="app_name">Scanbot SDK Example</string>
 
-    <string name="hello_world">Hello world!</string>
+
     <string name="action_settings">Settings</string>
 </resources>
diff --git a/classic-components-example/pdf-generation/src/main/res/xml/provider_paths.xml b/classic-components-example/pdf-generation/src/main/res/xml/provider_paths.xml
index ffa74ab5..8fc073a7 100644
--- a/classic-components-example/pdf-generation/src/main/res/xml/provider_paths.xml
+++ b/classic-components-example/pdf-generation/src/main/res/xml/provider_paths.xml
@@ -1,4 +1,5 @@
 <?xml version="1.0" encoding="utf-8"?>
 <paths xmlns:android="http://schemas.android.com/apk/res/android">
     <external-path name="external_files" path="."/>
+    <files-path name="scanbot_documents" path="scanbot-sdk/documents/"/>
 </paths>
\ No newline at end of file
diff --git a/classic-components-example/settings.gradle.kts b/classic-components-example/settings.gradle.kts
index 36996292..4cc318dd 100755
--- a/classic-components-example/settings.gradle.kts
+++ b/classic-components-example/settings.gradle.kts
@@ -26,6 +26,7 @@ include(
     ":edit-polygon-view",
     ":camera-fragment",
     ":document-scanner",
+    ":document-enhancer",
     ":barcode-scanner",
     ":mrz-scanner",
     ":mc-scanner",
diff --git a/classic-components-example/text-pattern-scanner/build.gradle b/classic-components-example/text-pattern-scanner/build.gradle
index 45947a16..f8b1aca9 100755
--- a/classic-components-example/text-pattern-scanner/build.gradle
+++ b/classic-components-example/text-pattern-scanner/build.gradle
@@ -17,21 +17,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/text-pattern-scanner/proguard-rules.pro b/classic-components-example/text-pattern-scanner/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/text-pattern-scanner/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/text-pattern-scanner/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/text-pattern-scanner/src/main/java/io/scanbot/example/MainActivity.kt
index eccea230..68966b3a 100755
--- a/classic-components-example/text-pattern-scanner/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/text-pattern-scanner/src/main/java/io/scanbot/example/MainActivity.kt
@@ -13,8 +13,8 @@ import androidx.core.content.ContextCompat
 import io.scanbot.example.common.applyEdgeToEdge
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
diff --git a/classic-components-example/text-pattern-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt b/classic-components-example/text-pattern-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
index c3c62f76..4e58f7aa 100644
--- a/classic-components-example/text-pattern-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
+++ b/classic-components-example/text-pattern-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
@@ -4,7 +4,6 @@ import android.os.Bundle
 import android.widget.Button
 import android.widget.TextView
 import androidx.appcompat.app.AppCompatActivity
-
 import io.scanbot.example.common.applyEdgeToEdge
 import io.scanbot.sdk.ScanbotSDK
 import io.scanbot.sdk.camera.CameraPreviewMode
@@ -21,7 +20,6 @@ class ScannerActivity : AppCompatActivity() {
     // @Tag("Text Pattern Custom UI")
     private lateinit var cameraView: IScanbotCameraView
     private lateinit var resultTextView: TextView
-    
     private var useFlash = false
 
     private lateinit var patternScanner: TextPatternScanner
@@ -30,14 +28,14 @@ class ScannerActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_scanner)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         cameraView = findViewById<ScanbotCameraXView>(R.id.cameraView)
         resultTextView = findViewById(R.id.resultTextView)
 
         val zoomFinderOverlay = findViewById<ZoomFinderOverlayView>(R.id.finder_overlay)
-        // The smaller finder view brings better performance and allows user to scan text more precise
+        // The smaller finder view brings better performance and allows the user to scan text more precisely
         zoomFinderOverlay.setRequiredAspectRatios(listOf(AspectRatio(4.0, 1.0)))
         zoomFinderOverlay.zoomLevel = 1.8f
 
@@ -47,10 +45,10 @@ class ScannerActivity : AppCompatActivity() {
         // TODO: set validation string and validation callback which matches the need of the task
         // For the pattern: # - digits, ? - for any character. Other characters represent themselves
         // In this example we are waiting for a string which starts with 1 or 2, and then 5 more digits
-        patternScanner.setConfiguration( patternScanner.copyCurrentConfiguration().copy(
+        patternScanner.setConfiguration(patternScanner.copyCurrentConfiguration().copy(
             // validator = PresetContentValidator(preset = ValidatorPreset.VEHICLE_IDENTIFICATION_NUMBER),
             // validator = PatternContentValidator(pattern = "######"),
-            validator = CustomContentValidator(callback =  object : ContentValidationCallback {
+            validator = CustomContentValidator(callback = object : ContentValidationCallback {
                 override fun clean(rawText: String): String {
                     return rawText.replace(" ", "_")
                 }
@@ -62,8 +60,10 @@ class ScannerActivity : AppCompatActivity() {
         ))
 
         patternScannerFrameHandler = TextPatternScannerFrameHandler.attach(cameraView, patternScanner)
-        patternScannerFrameHandler.addResultHandler { result, frame ->
-            val resultText: String = result.getOrNull()?.rawText ?:   result.errorOrNull()?.localizedMessage ?: "No result"
+        patternScannerFrameHandler.addResultHandler { result, _ ->
+            val resultText = result.getOrNull()?.rawText
+                ?: result.errorOrNull()?.localizedMessage
+                ?: "No result"
             runOnUiThread { resultTextView.text = resultText }
 
             false
diff --git a/classic-components-example/tiff-generation/build.gradle b/classic-components-example/tiff-generation/build.gradle
index baf5c167..349e84f5 100755
--- a/classic-components-example/tiff-generation/build.gradle
+++ b/classic-components-example/tiff-generation/build.gradle
@@ -17,16 +17,12 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     packagingOptions {
         exclude 'META-INF/LICENSE.txt'
         exclude 'META-INF/LICENSE'
@@ -40,6 +36,8 @@ android {
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/tiff-generation/proguard-rules.pro b/classic-components-example/tiff-generation/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/tiff-generation/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/tiff-generation/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/tiff-generation/src/main/java/io/scanbot/example/MainActivity.kt
index 99583449..5c26b392 100755
--- a/classic-components-example/tiff-generation/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/tiff-generation/src/main/java/io/scanbot/example/MainActivity.kt
@@ -9,6 +9,7 @@ import androidx.activity.result.contract.ActivityResultContracts
 import androidx.appcompat.app.AppCompatActivity
 import androidx.core.net.toUri
 import androidx.lifecycle.lifecycleScope
+import io.scanbot.common.onFailure
 import io.scanbot.example.common.Const
 import io.scanbot.example.common.applyEdgeToEdge
 import io.scanbot.example.common.getAppStorageDir
@@ -30,8 +31,8 @@ import java.io.File
 import java.util.UUID
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
@@ -94,27 +95,35 @@ class MainActivity : AppCompatActivity() {
         val result = withContext(Dispatchers.IO) {
 
             // Convert URIs to local files DON'T USE IN PRODUCTION
-            val files = imageUris.toTypedArray().map { uri ->
-
+            val files = imageUris.mapNotNull { uri ->
                 val file = appStorageDir.resolve(
                     UUID.randomUUID().toString() + ".jpg"
                 )
                 file.createNewFile()
+                val inputStream = contentResolver.openInputStream(uri)
+                if (inputStream == null) {
+                    Log.e(Const.LOG_TAG, "Cannot open input stream from URI: $uri")
+                    return@mapNotNull null
+                }
                 file.outputStream().use { output ->
-                    val openInputStream = contentResolver.openInputStream(uri)
-                    openInputStream.use { input ->
-                        input?.copyTo(output)
+                    inputStream.use { input ->
+                        input.copyTo(output)
                     }
                 }
                 file
             }
+            if (files.size != imageUris.size) {
+                return@withContext null
+            }
 
             tiffGenerator.generateFromFiles(
                 files,
                 false,
                 resultFile,
                 constructParameters(binarize, addCustomFields)
-            ).getOrNull()
+            ).onFailure {
+                Log.e(Const.LOG_TAG, "Error during TIFF generation: ${it.message}", it)
+            }.getOrNull()
         }
 
         withContext(Dispatchers.Main)
@@ -146,11 +155,6 @@ class MainActivity : AppCompatActivity() {
                     "custom_string_field_name",
                     UserFieldStringValue("testStringValue"),
                 ),
-                UserField(
-                    65001,
-                    "custom_number_field_name",
-                    UserFieldIntValue(100)
-                ),
                 UserField(
                     65535,
                     "custom_number_field_name",
diff --git a/classic-components-example/vin-scanner/build.gradle b/classic-components-example/vin-scanner/build.gradle
index deec7c50..a3f24aea 100755
--- a/classic-components-example/vin-scanner/build.gradle
+++ b/classic-components-example/vin-scanner/build.gradle
@@ -17,21 +17,19 @@ android {
 
     buildTypes {
         named("debug") {
-            // set this to `false` to allow debugging and run a "non-release" build
+            
             minifyEnabled = false
             debuggable = true
         }
     }
 
-    kotlin {
-        jvmToolchain(project.ext.jvmToolchainVersion)
-    }
-
     buildFeatures {
         viewBinding = true
     }
 }
 
+kotlin.jvmToolchain(project.ext.jvmToolchainVersion)
+
 dependencies {
     implementation(project(":common"))
     implementation("androidx.appcompat:appcompat:${project.ext.androidxAppcompatVersion}")
diff --git a/classic-components-example/vin-scanner/proguard-rules.pro b/classic-components-example/vin-scanner/proguard-rules.pro
deleted file mode 100755
index f1b42451..00000000
--- a/classic-components-example/vin-scanner/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
diff --git a/classic-components-example/vin-scanner/src/main/java/io/scanbot/example/MainActivity.kt b/classic-components-example/vin-scanner/src/main/java/io/scanbot/example/MainActivity.kt
index ee17bdd4..869dcaa9 100755
--- a/classic-components-example/vin-scanner/src/main/java/io/scanbot/example/MainActivity.kt
+++ b/classic-components-example/vin-scanner/src/main/java/io/scanbot/example/MainActivity.kt
@@ -13,8 +13,8 @@ import androidx.core.content.ContextCompat
 import io.scanbot.example.common.applyEdgeToEdge
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
+This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+Please check the official documentation for more details:
 Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
 ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
diff --git a/classic-components-example/vin-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt b/classic-components-example/vin-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
index 7192c0e9..cc5775dc 100644
--- a/classic-components-example/vin-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
+++ b/classic-components-example/vin-scanner/src/main/java/io/scanbot/example/ScannerActivity.kt
@@ -30,7 +30,7 @@ class ScannerActivity : AppCompatActivity() {
     override fun onCreate(savedInstanceState: Bundle?) {
         super.onCreate(savedInstanceState)
         setContentView(R.layout.activity_scanner)
-        supportActionBar!!.hide()
+        supportActionBar?.hide()
         applyEdgeToEdge(findViewById(R.id.root_view))
 
         vinScanner = ScanbotSDK(this).createVinScanner().getOrThrow()
diff --git a/compose-custom-ui-example/app/build.gradle b/compose-custom-ui-example/app/build.gradle
index 58d2ddbd..d7d661ed 100644
--- a/compose-custom-ui-example/app/build.gradle
+++ b/compose-custom-ui-example/app/build.gradle
@@ -12,7 +12,7 @@ android {
     defaultConfig {
         applicationId = "io.scanbot.example.compose"
         targetSdk = 35
-        minSdk = 21
+        minSdk = 23
         versionCode = 1
         versionName = "1.0"
 
@@ -71,7 +71,7 @@ dependencies {
     implementation("org.jetbrains.kotlinx:kotlinx-coroutines-core:$coroutines_version")
     implementation("org.jetbrains.kotlinx:kotlinx-coroutines-android:$coroutines_version")
 
-    def scanbotSdkVersion = "8.1.0"
+    def scanbotSdkVersion = "9.0.0.1206-SNAPSHOT"
 
     implementation("io.scanbot:sdk-package-4:$scanbotSdkVersion")
     implementation("io.scanbot:rtu-ui-v2-bundle:$scanbotSdkVersion")
diff --git a/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/DocumentTestScreens.kt b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/DocumentTestScreens.kt
index 9f4be563..141dfc7f 100644
--- a/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/DocumentTestScreens.kt
+++ b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/DocumentTestScreens.kt
@@ -299,4 +299,5 @@ private fun instructionString(status: DocumentDetectionStatus): String = when (s
     DocumentDetectionStatus.ERROR_PARTIALLY_VISIBLE_TOO_CLOSE -> "Please move the device away from the document"
     DocumentDetectionStatus.ERROR_TOO_DARK -> "Please turn on more light"
     DocumentDetectionStatus.ERROR_TOO_NOISY -> "Image is too noisy"
+    DocumentDetectionStatus.OK_BUT_ALREADY_CROPPED ->  "Already cropped, please move the device"
 }
diff --git a/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/barcode/BarcodeScannerSimpleSnippet.kt b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/barcode/BarcodeScannerSimpleSnippet.kt
new file mode 100644
index 00000000..4d4e0e6f
--- /dev/null
+++ b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/barcode/BarcodeScannerSimpleSnippet.kt
@@ -0,0 +1,52 @@
+package io.scanbot.example.compose.doc_code_snippet.barcode
+
+import android.util.Log
+import androidx.compose.foundation.layout.fillMaxSize
+import androidx.compose.runtime.Composable
+import androidx.compose.runtime.mutableFloatStateOf
+import androidx.compose.runtime.mutableStateOf
+import androidx.compose.runtime.remember
+import androidx.compose.ui.Alignment
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.unit.dp
+import io.scanbot.common.*
+import io.scanbot.example.compose.CustomBarcodesArView
+import io.scanbot.sdk.barcode.textWithExtension
+import io.scanbot.sdk.geometry.AspectRatio
+import io.scanbot.sdk.ui_v2.barcode.BarcodeScannerCustomUI
+import io.scanbot.sdk.ui_v2.common.CameraModule
+import io.scanbot.sdk.ui_v2.common.CameraPermissionScreen
+import io.scanbot.sdk.ui_v2.common.CameraPreviewMode
+import io.scanbot.sdk.ui_v2.common.components.FinderConfiguration
+import io.scanbot.sdk.ui_v2.common.components.ScanbotCameraPermissionView
+
+// @Tag("Simple Barcode Scanner Composable")
+@Composable
+fun BarcodeScannerSimpleSnippet() {
+    BarcodeScannerCustomUI(
+        // Modify Size here:
+        modifier = Modifier.fillMaxSize(),
+        permissionView = {
+            // View that will be shown while camera permission is not granted
+            // Use custom layout of camera permission handling view here:
+            ScanbotCameraPermissionView(
+                modifier = Modifier.fillMaxSize(),
+                bottomContentPadding = 0.dp,
+                permissionConfig = CameraPermissionScreen(),
+                onClose = {
+                    // Handle permission screen close if needed
+                })
+        },
+        onBarcodeScanningResult = { result ->
+            // See https://docs.scanbot.io/android/data-capture-modules/detailed-setup-guide/result-api/ for details of result handling
+            result.onSuccess { data ->
+                // Handle scanned barcodes here (for example, show a dialog or navigate to another screen)
+                Log.d(
+                    "BarcodeScannerScreen",
+                    "Scanned Barcodes: ${data.barcodes.joinToString { it.textWithExtension }}"
+                )
+            }
+        }
+    )
+}
+// @EndTag("Simple Barcode Scanner Composable")
diff --git a/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/document/DocumentScannerSimpleSnippet.kt b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/document/DocumentScannerSimpleSnippet.kt
new file mode 100644
index 00000000..b89a629a
--- /dev/null
+++ b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/document/DocumentScannerSimpleSnippet.kt
@@ -0,0 +1,158 @@
+package io.scanbot.example.compose.doc_code_snippet.document
+
+import android.graphics.Bitmap
+import android.util.Log
+import androidx.annotation.OptIn
+import androidx.camera.camera2.interop.ExperimentalCamera2Interop
+import androidx.compose.foundation.layout.Box
+import androidx.compose.foundation.layout.fillMaxSize
+import androidx.compose.foundation.layout.fillMaxWidth
+import androidx.compose.foundation.layout.height
+import androidx.compose.runtime.Composable
+import androidx.compose.runtime.mutableFloatStateOf
+import androidx.compose.runtime.mutableStateOf
+import androidx.compose.runtime.remember
+import androidx.compose.runtime.rememberCoroutineScope
+import androidx.compose.ui.Alignment
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.graphics.Color
+import androidx.compose.ui.platform.LocalContext
+import androidx.compose.ui.unit.dp
+import coil.compose.AsyncImage
+import io.scanbot.common.mapSuccess
+import io.scanbot.common.onFailure
+import io.scanbot.common.onSuccess
+import io.scanbot.sdk.ScanbotSDK
+import io.scanbot.sdk.camera.FrameHandler
+import io.scanbot.sdk.documentscanner.DocumentDetectionResult
+import io.scanbot.sdk.documentscanner.DocumentDetectionStatus
+import io.scanbot.sdk.documentscanner.DocumentScanner
+import io.scanbot.sdk.documentscanner.DocumentScannerConfiguration
+import io.scanbot.sdk.documentscanner.DocumentScannerParameters
+import io.scanbot.sdk.image.ImageRef
+import io.scanbot.sdk.imageprocessing.ScanbotSdkImageProcessor
+import io.scanbot.sdk.ui_v2.common.CameraModule
+import io.scanbot.sdk.ui_v2.common.CameraPermissionScreen
+import io.scanbot.sdk.ui_v2.common.CameraPreviewMode
+import io.scanbot.sdk.ui_v2.common.camera.TakePictureActionController
+import io.scanbot.sdk.ui_v2.common.components.ScanbotCameraPermissionView
+import io.scanbot.sdk.ui_v2.common.components.ScanbotSnapButton
+import io.scanbot.sdk.ui_v2.document.DocumentScannerCustomUI
+import io.scanbot.sdk.ui_v2.document.components.camera.ScanbotDocumentArOverlay
+import io.scanbot.sdk.ui_v2.document.screen.AutoSnappingConfiguration
+import kotlinx.coroutines.Dispatchers
+import kotlinx.coroutines.flow.SharedFlow
+import kotlinx.coroutines.launch
+
+// @Tag("Simple Document Scanner Composable")
+@Composable
+@OptIn(ExperimentalCamera2Interop::class)
+fun DocumentScannerSimpleSnippet() {
+    val context = LocalContext.current
+    val sdk = remember { ScanbotSDK(context) }
+    val imageProcessor = remember { ScanbotSdkImageProcessor.create() }
+    val documentScanner = remember { sdk.createDocumentScanner().getOrNull() }
+    val scope = rememberCoroutineScope()
+    val scannedImage = remember { mutableStateOf<Bitmap?>(null) }
+    val takePictureActionController =
+        remember { mutableStateOf<TakePictureActionController?>(null) }
+    val cameraInProcessingState = remember { mutableStateOf(false) }
+
+    Box(
+        modifier = Modifier
+            .fillMaxWidth(),
+    ) {
+        DocumentScannerCustomUI(
+            // Modify Size here:
+            modifier = Modifier.fillMaxSize(),
+            // Permission view that will be shown if camera permission is not granted
+            permissionView = {
+                // View that will be shown while camera permission is not granted
+                ScanbotCameraPermissionView(
+                    modifier = Modifier.fillMaxSize(),
+                    bottomContentPadding = 0.dp,
+                    permissionConfig = CameraPermissionScreen(),
+                    onClose = {
+                        // Handle permission screen close if needed
+                    })
+            },
+            // Triggered when picture is taken successfully and provides image for further processing
+            onPictureSnapped = { imageRef, captureInfo ->
+                // WARNING: move all processing operation to view model with proper coroutine scope in real apps to avoid data loss during recompositions
+                scope.launch(Dispatchers.Default) {
+                    scannedImage.value = createPreview(documentScanner, imageRef, imageProcessor)
+                    // Picture is received, allow auto-snapping again or proceed further and allow image snap after some additional processing
+                    cameraInProcessingState.value = false
+                }
+            },
+            // Provides TakePictureActionController to use for triggering picture taking manually
+            onTakePictureControllerCreated = {
+                takePictureActionController.value = it
+            },
+            // Callback that is called right before auto-snapping should be triggered.
+            // Return false to allow auto-snapping, true to prevent it.
+            onAutoSnapping = {
+                // return true if auto-snapping should be consumed and not proceed to take picture
+                cameraInProcessingState.value // Disable auto-snapping while awaiting picture result after snap is triggered
+            },
+            // Callback invoked after each frame with document scanning result.
+            onDocumentScanningResult = { result ->
+                result.onSuccess { data ->
+                    // Handle scanned barcodes here (for example, show a dialog)
+                    val points = data.pointsNormalized
+                    val status = data.status
+                }
+            },
+        )
+        ScanbotSnapButton(
+            modifier = Modifier
+                .height(100.dp)
+                .align(Alignment.BottomCenter),
+            // Disable button when scanning or auto-snapping is disabled
+            clickable =  !cameraInProcessingState.value,
+            // Show indicator  that camera in auto-snapping mode
+            autoCapture = true,
+            // Animate progress when camera is processing the last taken picture
+            animateProgress = cameraInProcessingState.value,
+        ) {
+            takePictureActionController.value?.invoke()
+        }
+
+        // Simple view that shows scanned image preview
+        if (scannedImage.value != null) {
+            AsyncImage(
+                model = scannedImage.value,
+                contentDescription = "ScannedImage",
+                modifier = Modifier
+                    .height(100.dp)
+                    .align(Alignment.BottomEnd)
+            )
+        }
+    }
+}
+
+private fun createPreview(
+    documentScanner: DocumentScanner?,
+    imageRef: ImageRef,
+    imageProcessor: ScanbotSdkImageProcessor,
+): Bitmap? {
+    // See https://docs.scanbot.io/android/data-capture-modules/detailed-setup-guide/result-api/ for details of result handling
+    // run detection and cropping on the captured image
+    return documentScanner?.run(imageRef)?.mapSuccess { documentData ->
+        val croppedImage =
+            imageProcessor.crop(imageRef, documentData.pointsNormalized)
+                .getOrReturn() // get the result of cropping operation or leave onSuccess if cropping failed
+        imageRef.close() // clear image ref resources
+
+        val downscaledCrop = imageProcessor.resize(croppedImage, 300).getOrReturn().toBitmap()
+            .getOrReturn() // get the result of cropping operation or leave onSuccess if cropping failed
+        croppedImage.close() // clear image ref resources
+        downscaledCrop
+    }?.onFailure { error ->
+        Log.e(
+            "DocumentScannerScreen",
+            "Document scanning error: ${error.message}"
+        )
+    }?.getOrNull()
+}
+// @EndTag("Simple Document Scanner Composable")
diff --git a/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/document/DocumentScannerSnippet.kt b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/document/DocumentScannerSnippet.kt
index 74694862..de0ec469 100644
--- a/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/document/DocumentScannerSnippet.kt
+++ b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/document/DocumentScannerSnippet.kt
@@ -193,7 +193,7 @@ fun DocumentScannerSnippet() {
             // Callback invoked after each frame with document scanning result.
             onDocumentScanningResult = { result ->
                 result.onSuccess { data ->
-                    // Handle scanned barcodes here (for example, show a dialog)
+                    // Handle scanned polygon data here (for example, show a dialog)
                     val points = data.pointsNormalized
                     val status = data.status
                 }
diff --git a/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/mrz/MrzScannerSimpleSnippet.kt b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/mrz/MrzScannerSimpleSnippet.kt
new file mode 100644
index 00000000..5d170f82
--- /dev/null
+++ b/compose-custom-ui-example/app/src/main/java/io/scanbot/example/compose/doc_code_snippet/mrz/MrzScannerSimpleSnippet.kt
@@ -0,0 +1,48 @@
+package io.scanbot.example.compose.doc_code_snippet.mrz
+
+import android.util.Log
+import androidx.compose.foundation.layout.fillMaxSize
+import androidx.compose.runtime.Composable
+import androidx.compose.runtime.mutableFloatStateOf
+import androidx.compose.runtime.mutableStateOf
+import androidx.compose.runtime.remember
+import androidx.compose.ui.Alignment
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.unit.dp
+import io.scanbot.common.*
+import io.scanbot.sdk.geometry.*
+import io.scanbot.sdk.ui_v2.common.*
+import io.scanbot.sdk.ui_v2.common.components.*
+import io.scanbot.sdk.ui_v2.mrz.*
+
+// @Tag("Simple MRZ Scanner Composable")
+@Composable
+fun MrzScannerSimpleSnippet() {
+    MrzScannerCustomUI(
+        // Modify Size here:
+        modifier = Modifier
+            .fillMaxSize(),
+        // Permission view that will be shown if camera permission is not granted
+        permissionView = {
+            // View that will be shown while camera permission is not granted
+            // Use custom layout of camera permission handling view here:
+            ScanbotCameraPermissionView(
+                modifier = Modifier.fillMaxSize(),
+                bottomContentPadding = 0.dp,
+                permissionConfig = CameraPermissionScreen(),
+                onClose = {
+                    // Handle permission screen close if needed
+                })
+        },
+        onMrzScanningResult = { result ->
+            // See https://docs.scanbot.io/android/data-capture-modules/detailed-setup-guide/result-api/ for details of result handling
+            result.onSuccess { data ->
+                // Handle scanned barcodes here (for example, show a dialog or navigate to another screen)
+                Log.d(
+                    "MrzScannerScreen", "Scanned mrz: ${data.rawMRZ}"
+                )
+            }
+        }
+    )
+}
+// @EndTag("Simple MRZ Scanner Composable")
diff --git a/compose-custom-ui-example/build.gradle b/compose-custom-ui-example/build.gradle
index 16f7a52d..af8b1b74 100644
--- a/compose-custom-ui-example/build.gradle
+++ b/compose-custom-ui-example/build.gradle
@@ -1,6 +1,6 @@
 
 plugins {
-    id "com.android.application" version '8.9.0' apply false
+    id "com.android.application" version '8.9.1' apply false
     id "org.jetbrains.kotlin.android" version "2.2.20" apply false
     id "org.jetbrains.kotlin.plugin.compose" version "2.2.20" apply false
 }
diff --git a/data-capture-ready-to-use-ui-example/README.md b/data-capture-ready-to-use-ui-example/README.md
new file mode 100644
index 00000000..504fd084
--- /dev/null
+++ b/data-capture-ready-to-use-ui-example/README.md
@@ -0,0 +1,19 @@
+# Scanbot Data Capture Ready-To-Use UI example
+
+This project demonstrates the Scanbot SDK Ready‑To‑Use UI for data capture modules (MRZ, VIN, text pattern, checks, credit cards, document data extraction, and more).
+
+## Requirements
+
+- Latest stable Android Studio
+- JDK 17
+
+## How to run
+
+1. Open `scanbot-sdk-example-android/data-capture-ready-to-use-ui-example` in Android Studio.
+2. Sync Gradle.
+3. Add your license key in `Application`.
+4. Run the app on a device or emulator.
+
+## Obfuscation
+
+Minification is disabled in this example and no custom ProGuard/R8 rules are provided. If you enable minification, add your own rules and follow the Scanbot SDK obfuscation guidance from the official documentation.
diff --git a/data-capture-ready-to-use-ui-example/app/build.gradle b/data-capture-ready-to-use-ui-example/app/build.gradle
index fae161b3..8301b965 100644
--- a/data-capture-ready-to-use-ui-example/app/build.gradle
+++ b/data-capture-ready-to-use-ui-example/app/build.gradle
@@ -12,7 +12,7 @@ android {
     defaultConfig {
         applicationId = "io.scanbot.example.sdk.rtu.android"
         targetSdk = 35
-        minSdk = 21
+        minSdk = 23
         versionCode = 1
         versionName = "1.0"
 
@@ -31,7 +31,7 @@ android {
         }
         named("release") {
             // set this to `false` to allow debugging and run a "non-release" build
-            minifyEnabled = true
+            minifyEnabled = false
             debuggable = true
         }
     }
@@ -54,10 +54,6 @@ android {
     }
 }
 
-kapt {
-    generateStubs = true
-}
-
 configurations {
     compile.exclude group: "org.jetbrains", module: "annotations"
 }
@@ -74,7 +70,7 @@ dependencies {
     implementation("org.jetbrains.kotlinx:kotlinx-coroutines-core:$coroutines_version")
     implementation("org.jetbrains.kotlinx:kotlinx-coroutines-android:$coroutines_version")
 
-    def scanbotSdkVersion = "8.1.0"
+    def scanbotSdkVersion = "9.0.0.1206-SNAPSHOT"
 
     implementation("io.scanbot:sdk-package-4:$scanbotSdkVersion")
     implementation("io.scanbot:rtu-ui-v2-bundle:$scanbotSdkVersion")
diff --git a/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/Application.kt b/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/Application.kt
index 53af5b96..9ad5f23b 100644
--- a/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/Application.kt
+++ b/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/Application.kt
@@ -31,7 +31,7 @@ class Application : Application(), CoroutineScope {
          * Please note: The Scanbot SDK will run without a license key for one minute per session!
          * After the trial period is over all Scanbot SDK functions as well as the UI components will stop working.
          * You can get an unrestricted "no-strings-attached" 30 day trial license key for free.
-         * Please submit the trial license form (https://scanbot.io/sdk/trial.html) on our website by using
+         * Please submit the trial license form (https://scanbot.io/trial/) on our website by using
          * the app identifier "io.scanbot.example.sdk.rtu.android" of this example app.
          */
         const val LICENSE_KEY = ""
diff --git a/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/util/FontSpan.kt b/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/util/FontSpan.kt
index fc0bccc4..5637aa2e 100644
--- a/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/util/FontSpan.kt
+++ b/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/util/FontSpan.kt
@@ -13,11 +13,17 @@ open class FontSpan(private val font: Typeface) : MetricAffectingSpan() {
     private fun update(textPaint: TextPaint) {
         textPaint.apply {
             val old = typeface
-            val oldStyle = old?.style ?: 0
+            val oldStyle = old?.style ?: Typeface.NORMAL
+            val normalizedStyle = when (oldStyle) {
+                Typeface.BOLD,
+                Typeface.ITALIC,
+                Typeface.BOLD_ITALIC -> oldStyle
+                else -> Typeface.NORMAL
+            }
 
             // keep the style set before
-            val font = Typeface.create(font, oldStyle)
-            typeface = font
+            val updatedTypeface = Typeface.create(font, normalizedStyle)
+            typeface = updatedTypeface
         }
     }
-}
\ No newline at end of file
+}
diff --git a/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/util/GalleryUtils.kt b/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/util/GalleryUtils.kt
index f2904773..3861e218 100644
--- a/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/util/GalleryUtils.kt
+++ b/data-capture-ready-to-use-ui-example/app/src/main/java/io/scanbot/example/util/GalleryUtils.kt
@@ -38,24 +38,35 @@ fun Uri.toBitmap(
 ): Bitmap? {
     val maxImageSideSize = 4090
     try {
-        var bitmap: Bitmap? = null
-
         val input = contentResolver.openInputStream(this)
+            ?: run {
+                onException(IllegalStateException("Cannot open input stream from URI: $this"))
+                return null
+            }
         var orientation = 0
 
-        input.use {
+        input.use { stream ->
             if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
-                val exif = ExifInterface(input!!)
+                val exif = ExifInterface(stream)
                 orientation = exifToGrad(exif.getAttributeInt(ExifInterface.TAG_ORIENTATION, 0))
             }
         }
         val inputNew = contentResolver.openInputStream(this)
+            ?: run {
+                onException(IllegalStateException("Cannot open input stream from URI: $this"))
+                return null
+            }
 
-        bitmap = inputNew.use { BitmapFactory.decodeStream(inputNew) }
+        val decodedBitmap = inputNew.use { BitmapFactory.decodeStream(it) }
+        if (decodedBitmap == null) {
+            onException(IllegalStateException("Failed to decode image from URI: $this"))
+            return null
+        }
 
+        var bitmap = decodedBitmap
         val width = bitmap.width
         val height = bitmap.height
-        if (bitmap != null && (orientation != 0 || width > maxImageSideSize || height > maxImageSideSize)) {
+        if (orientation != 0 || width > maxImageSideSize || height > maxImageSideSize) {
             val matrix = Matrix()
             if (orientation != 0) {
                 matrix.setRotate(orientation.toFloat(), width / 2f, height / 2f)
diff --git a/data-capture-ready-to-use-ui-example/build.gradle b/data-capture-ready-to-use-ui-example/build.gradle
index 0421943d..8eec520a 100644
--- a/data-capture-ready-to-use-ui-example/build.gradle
+++ b/data-capture-ready-to-use-ui-example/build.gradle
@@ -1,6 +1,6 @@
 
 plugins {
-    id "com.android.application" version '8.9.0' apply false
+    id "com.android.application" version '8.9.1' apply false
     id "org.jetbrains.kotlin.android" version "2.2.20" apply false
 }
 
diff --git a/document-scanner-ready-to-use-ui-example/README.md b/document-scanner-ready-to-use-ui-example/README.md
index 6fa49132..45f9efc5 100644
--- a/document-scanner-ready-to-use-ui-example/README.md
+++ b/document-scanner-ready-to-use-ui-example/README.md
@@ -24,3 +24,9 @@ framework or features, please visit our [Support Page](https://docs.scanbot.io/s
 
 👉 [Scanbot Document Scanner SDK documentation](https://docs.scanbot.io/document-scanner-sdk/android/introduction/)
 
+## How to run
+
+1. Open `scanbot-sdk-example-android/document-scanner-ready-to-use-ui-example` in Android Studio.
+2. Sync Gradle.
+3. Add your license key in `ExampleApplication` or stay in demo mode.
+4. Run the app on a device or emulator.
diff --git a/document-scanner-ready-to-use-ui-example/app/build.gradle b/document-scanner-ready-to-use-ui-example/app/build.gradle
index c42b895b..63f88fa5 100644
--- a/document-scanner-ready-to-use-ui-example/app/build.gradle
+++ b/document-scanner-ready-to-use-ui-example/app/build.gradle
@@ -10,7 +10,7 @@ android {
 
     defaultConfig {
         applicationId = "io.scanbot.example.document.usecases.android"
-        minSdk = 21
+        minSdk = 23
         targetSdk = 35
         versionCode = 1
         versionName = "1.0"
@@ -21,12 +21,10 @@ android {
             minifyEnabled = false
             shrinkResources = false
             debuggable = true
-            proguardFiles(getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro")
         }
         named("release") {
             minifyEnabled = false
             debuggable = true
-            proguardFiles(getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro")
         }
     }
 
@@ -39,7 +37,7 @@ android {
     }
 }
 
-def scanbotSdkVersion =  "8.1.0"
+def scanbotSdkVersion =  "9.0.0.1206-SNAPSHOT"
 
 dependencies {
 
diff --git a/document-scanner-ready-to-use-ui-example/app/proguard-rules.pro b/document-scanner-ready-to-use-ui-example/app/proguard-rules.pro
deleted file mode 100644
index 481bb434..00000000
--- a/document-scanner-ready-to-use-ui-example/app/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-#   http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-#   public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
\ No newline at end of file
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/di/ExampleSingleton.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/di/ExampleSingleton.kt
index 84cf1668..e221e21b 100644
--- a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/di/ExampleSingleton.kt
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/di/ExampleSingleton.kt
@@ -11,10 +11,10 @@ import io.scanbot.sdk.persistence.page.PageFileStorage
 import io.scanbot.sdk.tiff.TiffGeneratorManager
 
 /**
-Ths example uses new sdk APIs presented in Scanbot SDK v.8.x.x
-Please, check the official documentation for more details:
-Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
-ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
+ * This example uses the SDK APIs introduced in Scanbot SDK v8.x.x.
+ * Please check the official documentation for more details:
+ * Result API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/result-api/
+ * ImageRef API https://docs.scanbot.io/android/document-scanner-sdk/detailed-setup-guide/image-ref-api/
  */
 
 /** This singleton is used only for simplicity. Please, use Hilt or other DI framework in production code. */
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentDetectionSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentDetectionSnippet.kt
index 3d5c380e..af9af00e 100644
--- a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentDetectionSnippet.kt
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentDetectionSnippet.kt
@@ -44,7 +44,7 @@ class DocumentDetectionSnippet : AppCompatActivity() {
                                     .forEach { image ->
                                         if (image == null) {
                                             Log.e(
-                                                "StandaloneCropSnippet",
+                                                "DocumentDetectionSnippet",
                                                 "Failed to load image from URI"
                                             )
                                             return@forEach
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentQualityCheckSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentQualityCheckSnippet.kt
index a2164c38..71cd214a 100644
--- a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentQualityCheckSnippet.kt
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentQualityCheckSnippet.kt
@@ -16,6 +16,7 @@ import io.scanbot.common.onSuccess
 import io.scanbot.sdk.ScanbotSDK
 import io.scanbot.sdk.docprocessing.Document
 import io.scanbot.sdk.documentqualityanalyzer.DocumentQuality
+import io.scanbot.sdk.documentqualityanalyzer.DocumentQualityAssessment
 import io.scanbot.sdk.util.toImageRef
 
 
@@ -43,14 +44,14 @@ class DocumentQualityCheckSnippet : AppCompatActivity() {
                                     .forEach { image ->
                                         if (image == null) {
                                             Log.e(
-                                                "StandaloneCropSnippet",
+                                                "QualityCheckSnippet",
                                                 "Failed to load image from URI"
                                             )
                                             return@forEach
                                         }
                                         document.addPage(image)
                                     }
-                                startCropping(document)
+                                startDqa(document)
                             }
                         }
                     }
@@ -62,7 +63,7 @@ class DocumentQualityCheckSnippet : AppCompatActivity() {
     // Create a document detector instance
     val qualityAnalyzer = scanbotSDK.createDocumentQualityAnalyzer().getOrNull()
 
-    fun startCropping(document: Document) {
+    fun startDqa(document: Document) {
         document.pages.forEach { page ->
             // Run quality check on the created page
             val documentQuality =
@@ -76,13 +77,11 @@ class DocumentQualityCheckSnippet : AppCompatActivity() {
     // @EndTag("Analyze the quality of a document image")
 
     // Print the result.
-    fun printResult(quality: DocumentQuality?) {
+    fun printResult(quality: DocumentQualityAssessment?) {
         when (quality) {
-            DocumentQuality.VERY_POOR -> print("The quality of the document is very poor")
-            DocumentQuality.POOR -> print("The quality of the document is poor")
-            DocumentQuality.REASONABLE -> print("The quality of the document is reasonable")
-            DocumentQuality.GOOD -> print("The quality of the document is good")
-            DocumentQuality.EXCELLENT -> print("The quality of the document is excellent")
+            DocumentQualityAssessment.ACCEPTABLE ->  print("The quality of the document is good enough for processing.")
+            DocumentQualityAssessment.UNACCEPTABLE ->  print("The quality of the document is not good enough for processing.")
+            DocumentQualityAssessment.UNCERTAIN -> print("The quality of the document is uncertain. It may be good enough for processing, but there is a risk that the result will not be good.")
             else -> print("No document was found")
         }
     }
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentStraighteningSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentStraighteningSnippet.kt
new file mode 100644
index 00000000..25aa77db
--- /dev/null
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/DocumentStraighteningSnippet.kt
@@ -0,0 +1,95 @@
+package com.example.scanbot.doc_code_snippet
+
+
+import android.app.Activity
+import android.content.Intent
+import android.os.Bundle
+import android.util.Log
+import androidx.activity.result.contract.ActivityResultContracts
+import androidx.appcompat.app.AppCompatActivity
+import androidx.lifecycle.lifecycleScope
+import com.example.scanbot.utils.getUrisFromGalleryResult
+import kotlinx.coroutines.Dispatchers
+import kotlinx.coroutines.launch
+import kotlinx.coroutines.withContext
+import io.scanbot.common.onSuccess
+import io.scanbot.page.PageImageSource
+import io.scanbot.sdk.ScanbotSDK
+import io.scanbot.sdk.docprocessing.Document
+import io.scanbot.sdk.documentscanner.DocumentStraighteningMode
+import io.scanbot.sdk.documentscanner.DocumentStraighteningParameters
+import io.scanbot.sdk.geometry.AspectRatio
+import io.scanbot.sdk.util.isDefault
+import io.scanbot.sdk.util.toImageRef
+
+
+class DocumentStraighteningSnippet : AppCompatActivity() {
+
+    override fun onCreate(savedInstanceState: Bundle?) {
+        super.onCreate(savedInstanceState)
+        // In the real application, you should call this function on button click
+        importImagesFromLibrary()
+    }
+
+    private val scanbotSDK = ScanbotSDK(this@DocumentStraighteningSnippet)
+    private val context = this
+
+    private val pictureForDocDetectionResult =
+        this.registerForActivityResult(ActivityResultContracts.StartActivityForResult()) { activityResult ->
+            if (activityResult.resultCode == Activity.RESULT_OK) {
+                activityResult.data?.let { imagePickerResult ->
+                    lifecycleScope.launch {
+                        withContext(Dispatchers.Default) {
+                            scanbotSDK.documentApi.createDocument().onSuccess { document ->
+                                getUrisFromGalleryResult(imagePickerResult)
+                                    .asSequence() // process images one by one instead of collecting the whole list - less memory consumption
+                                    .map { it.toImageRef(contentResolver).getOrNull() }
+                                    .forEach { image ->
+                                        if (image == null) {
+                                            Log.e(
+                                                "StraighteningSnippet",
+                                                "Failed to load image from URI"
+                                            )
+                                            return@forEach
+                                        }
+                                        document.addPage(image)
+                                    }
+                                startStraightening(document)
+                            }
+                        }
+                    }
+                }
+            }
+        }
+
+    // @Tag("Direct Document straightening on page")
+    fun startStraightening(document: Document) {
+        document.pages.forEach { page ->
+            page.apply(
+                newStraighteningParameters = DocumentStraighteningParameters(
+                    straighteningMode = DocumentStraighteningMode.STRAIGHTEN,
+                    // Expected aspect ratios for the documents. Comment if unknown.
+                    aspectRatios = listOf(AspectRatio(3.0, 4.0))
+                )
+            )
+            // Set the source of the page to IMPORTED if needs
+            page.source = PageImageSource.IMPORTED
+        }
+    }
+    // @EndTag("Direct Document straightening on page")
+
+    private fun importImagesFromLibrary() {
+        val imageIntent = Intent()
+        imageIntent.type = "image/*"
+        imageIntent.action = Intent.ACTION_GET_CONTENT
+        imageIntent.putExtra(Intent.EXTRA_LOCAL_ONLY, false)
+        imageIntent.putExtra(Intent.EXTRA_ALLOW_MULTIPLE, false)
+        imageIntent.putExtra(
+            Intent.EXTRA_MIME_TYPES,
+            arrayOf("image/jpeg", "image/png", "image/webp", "image/heic")
+        )
+        pictureForDocDetectionResult.launch(Intent.createChooser(imageIntent, "Select Picture"))
+    }
+
+}
+
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImageQualityCheckSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImageQualityCheckSnippet.kt
index 12d0605b..2d4a7684 100644
--- a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImageQualityCheckSnippet.kt
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImageQualityCheckSnippet.kt
@@ -13,6 +13,7 @@ import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 import io.scanbot.sdk.ScanbotSDK
 import io.scanbot.sdk.documentqualityanalyzer.DocumentQuality
+import io.scanbot.sdk.documentqualityanalyzer.DocumentQualityAssessment
 import io.scanbot.sdk.image.ImageRef
 import io.scanbot.sdk.util.toImageRef
 
@@ -62,13 +63,11 @@ class ImageQualityCheckSnippet : AppCompatActivity() {
     // @EndTag("Analyze the quality of an image")
 
     // Print the result.
-    fun printResult(quality: DocumentQuality?) {
+    fun printResult(quality: DocumentQualityAssessment?) {
         when (quality) {
-            DocumentQuality.VERY_POOR -> print("The quality of the document is very poor")
-            DocumentQuality.POOR -> print("The quality of the document is poor")
-            DocumentQuality.REASONABLE -> print("The quality of the document is reasonable")
-            DocumentQuality.GOOD -> print("The quality of the document is good")
-            DocumentQuality.EXCELLENT -> print("The quality of the document is excellent")
+            DocumentQualityAssessment.ACCEPTABLE ->  print("The quality of the document is good enough for processing.")
+            DocumentQualityAssessment.UNACCEPTABLE ->  print("The quality of the document is not good enough for processing.")
+            DocumentQualityAssessment.UNCERTAIN -> print("The quality of the document is uncertain. It may be good enough for processing, but there is a risk that the result will not be good.")
             else -> print("No document was found")
         }
     }
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImageStraighteningSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImageStraighteningSnippet.kt
new file mode 100644
index 00000000..614af4d4
--- /dev/null
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImageStraighteningSnippet.kt
@@ -0,0 +1,93 @@
+package com.example.scanbot.doc_code_snippet
+
+
+import android.app.Activity
+import android.content.Intent
+import android.os.Bundle
+import android.util.Log
+import androidx.activity.result.contract.ActivityResultContracts
+import androidx.appcompat.app.AppCompatActivity
+import androidx.lifecycle.lifecycleScope
+import com.example.scanbot.utils.getUrisFromGalleryResult
+import kotlinx.coroutines.Dispatchers
+import kotlinx.coroutines.launch
+import kotlinx.coroutines.withContext
+import io.scanbot.common.onFailure
+import io.scanbot.common.onSuccess
+import io.scanbot.page.PageImageSource
+import io.scanbot.sdk.ScanbotSDK
+import io.scanbot.sdk.docprocessing.Document
+import io.scanbot.sdk.documentscanner.DocumentStraighteningMode
+import io.scanbot.sdk.documentscanner.DocumentStraighteningParameters
+import io.scanbot.sdk.geometry.AspectRatio
+import io.scanbot.sdk.image.ImageRef
+import io.scanbot.sdk.util.isDefault
+import io.scanbot.sdk.util.toImageRef
+
+
+class ImageStraighteningSnippet : AppCompatActivity() {
+
+    override fun onCreate(savedInstanceState: Bundle?) {
+        super.onCreate(savedInstanceState)
+        // In the real application, you should call this function on button click
+        importImagesFromLibrary()
+    }
+
+    private val scanbotSDK = ScanbotSDK(this@ImageStraighteningSnippet)
+    private val context = this
+
+    private val pictureForDocDetectionResult =
+        this.registerForActivityResult(ActivityResultContracts.StartActivityForResult()) { activityResult ->
+            if (activityResult.resultCode == RESULT_OK) {
+                activityResult.data?.let { imagePickerResult ->
+                    lifecycleScope.launch {
+                        withContext(Dispatchers.Default) {
+                            getUrisFromGalleryResult(imagePickerResult)
+                                .asSequence() // process images one by one instead of collecting the whole list - less memory consumption
+                                .map { it.toImageRef(contentResolver).getOrNull() }
+                                .forEach { image ->
+                                    if (image == null) {
+                                        Log.e(
+                                            "StraighteningSnippet",
+                                            "Failed to load image from URI"
+                                        )
+                                        return@forEach
+                                    }
+                                    startStraightening(image)
+                                }
+                        }
+                    }
+                }
+            }
+        }
+
+    // @Tag("Direct Document straightening on image")
+    fun startStraightening(imageRef: ImageRef) {
+       scanbotSDK.createDocumentEnhancer().onSuccess { enhancer ->
+           val params =   DocumentStraighteningParameters(
+               straighteningMode = DocumentStraighteningMode.STRAIGHTEN,
+               // Expected aspect ratios for the documents. Comment if unknown.
+               aspectRatios = listOf(AspectRatio(3.0, 4.0))
+           )
+           enhancer.straighten(imageRef, params).onSuccess { result ->
+               //  result.straightenedImage is an ImageRef of the straightened image, you can display it in the UI or save it to storage
+           }
+       }
+    }
+    // @EndTag("Direct Document straightening on image")
+
+    private fun importImagesFromLibrary() {
+        val imageIntent = Intent()
+        imageIntent.type = "image/*"
+        imageIntent.action = Intent.ACTION_GET_CONTENT
+        imageIntent.putExtra(Intent.EXTRA_LOCAL_ONLY, false)
+        imageIntent.putExtra(Intent.EXTRA_ALLOW_MULTIPLE, false)
+        imageIntent.putExtra(
+            Intent.EXTRA_MIME_TYPES,
+            arrayOf("image/jpeg", "image/png", "image/webp", "image/heic")
+        )
+        pictureForDocDetectionResult.launch(Intent.createChooser(imageIntent, "Select Picture"))
+    }
+
+}
+
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImportDocumentFromPdfSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImportDocumentFromPdfSnippet.kt
index 032b9e23..629bb44c 100644
--- a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImportDocumentFromPdfSnippet.kt
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImportDocumentFromPdfSnippet.kt
@@ -54,14 +54,14 @@ class ImportDocumentFromPdfSnippet : AppCompatActivity() {
     val extractor = scanbotSDK.createPdfImagesExtractor()
     fun createDocumentFromPdf(list: List<Uri>) {
         list.forEach { pdfUri ->
-            extractor.imageUrlsFromPdf(
+            extractor.extract(
                 pdfFile = pdfUri.toFile(),
                 outputDir = File("path/to/output/folder"),
                 prefix = "image_"
             ).apply {
                 scanbotSDK.documentApi.createDocument().onSuccess { document ->
-                    this@apply.forEach { imageUri ->
-                        val bitmap = BitmapFactory.decodeFile(imageUri.toFile().absolutePath)
+                    document.pages.forEach { page ->
+                        val bitmap = BitmapFactory.decodeFile(page.documentFileUri.toFile().absolutePath)
                         if (bitmap == null) {
                             Log.e(
                                 "Snippet",
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImportImagesFromPdfSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImportImagesFromPdfSnippet.kt
index f9b568f8..89b77b22 100644
--- a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImportImagesFromPdfSnippet.kt
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/ImportImagesFromPdfSnippet.kt
@@ -14,6 +14,7 @@ import kotlinx.coroutines.Dispatchers
 import kotlinx.coroutines.launch
 import kotlinx.coroutines.withContext
 import java.io.File
+import io.scanbot.common.onSuccess
 import io.scanbot.sdk.ScanbotSDK
 
 
@@ -51,12 +52,12 @@ class ImportImagesFromPdfSnippet : AppCompatActivity() {
     val extractor = scanbotSDK.createPdfImagesExtractor()
     fun createDocumentFromPdf(list: List<Uri>) {
         list.forEach { pdfUri ->
-            val images = extractor.imageUrlsFromPdf(
+            val images = extractor.extract(
                 pdfFile = pdfUri.toFile(),
                 outputDir = File("path/to/output/folder"),
                 prefix = "image_"
             )
-            if (images.isNotEmpty()) {
+           images.onSuccess { imageFiles ->
                 // do something with the images
             }
         }
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/rtu_ui/AcknowledgeScreenSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/rtu_ui/AcknowledgeScreenSnippet.kt
index 08bd4300..5aee043c 100644
--- a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/rtu_ui/AcknowledgeScreenSnippet.kt
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/rtu_ui/AcknowledgeScreenSnippet.kt
@@ -59,24 +59,24 @@ class AcknowledgeScreenSnippet : AppCompatActivity() {
                 // - `NONE`: Skips the quality check entirely.
                 acknowledgementMode = AcknowledgementMode.ALWAYS
 
-                // Set the minimum acceptable document quality.
-                // Options: excellent, good, reasonable, poor, veryPoor, or noDocument.
-                minimumQuality = DocumentQuality.GOOD
-
                 // Set the background color for the acknowledgment screen.
                 backgroundColor = ScanbotColor(value = "#EFEFEF")
 
                 // You can also configure the buttons in the bottom bar of the acknowledgment screen.
                 // e.g To force the user to retake, if the captured document is not OK.
-                bottomBar.acceptWhenNotOkButton.visible = false
+                bottomBar.proceedAnywayButton.visible = false
 
                 // Hide the titles of the buttons.
-                bottomBar.acceptWhenNotOkButton.title.visible = false
-                bottomBar.acceptWhenOkButton.title.visible = false
+                bottomBar.proceedAnywayButton.documentNotFound.title.visible = false
+                bottomBar.proceedAnywayButton.uncertainQuality.title.visible = false
+                bottomBar.proceedAnywayButton.unacceptableQuality.title.visible = false
+                bottomBar.acceptWhenAcceptableButton.title.visible = false
                 bottomBar.retakeButton.title.visible = false
 
                 // Configure the acknowledgment screen's hint message which is shown if the least acceptable quality is not met.
-                badImageHint.visible = true
+                documentNotFoundWarning.visible = true
+                uncertainQualityWarning.visible = true
+                unacceptableQualityWarning.visible = true
             }
         }
 
diff --git a/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/rtu_ui/DocumentStraighteningSnippet.kt b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/rtu_ui/DocumentStraighteningSnippet.kt
new file mode 100644
index 00000000..0e1487fc
--- /dev/null
+++ b/document-scanner-ready-to-use-ui-example/app/src/main/java/com/example/scanbot/doc_code_snippet/rtu_ui/DocumentStraighteningSnippet.kt
@@ -0,0 +1,66 @@
+package com.example.scanbot.doc_code_snippet.rtu_ui
+
+
+import android.os.Bundle
+import androidx.activity.result.ActivityResultLauncher
+import androidx.appcompat.app.AppCompatActivity
+import io.scanbot.common.Result
+import io.scanbot.common.onCancellation
+import io.scanbot.common.onFailure
+import io.scanbot.common.onSuccess
+import io.scanbot.sdk.documentscanner.DocumentStraighteningMode
+import io.scanbot.sdk.documentscanner.DocumentStraighteningParameters
+import io.scanbot.sdk.geometry.AspectRatio
+
+import io.scanbot.sdk.ui_v2.document.DocumentScannerActivity
+import io.scanbot.sdk.ui_v2.document.configuration.DocumentScanningFlow
+
+
+class DocumentStraighteningSnippet : AppCompatActivity() {
+    override fun onCreate(savedInstanceState: Bundle?) {
+        super.onCreate(savedInstanceState)
+        // In the real application, you should call this function on button click
+        startScanning()
+    }
+
+    private val context = this
+    private val documentScannerResult: ActivityResultLauncher<DocumentScanningFlow> by lazy {
+        registerForActivityResult(DocumentScannerActivity.ResultContract()) { result ->
+            result.onSuccess { document ->
+                // Handle the scanned document.
+            }.onCancellation {
+                // Indicates that the cancel button was tapped. Or screen is closed by other reason.
+            }.onFailure {
+                when (it) {
+                    is Result.InvalidLicenseError -> {
+                        // indicate that the Scanbot SDK license is invalid
+                    }
+
+                    else -> {
+                        // Handle other errors
+                    }
+                }
+            }
+        }
+    }
+
+    // @Tag("Set Document Straightening Parameters")
+    fun startScanning() {
+        // Create the default configuration object.
+        val configuration = DocumentScanningFlow().apply {
+            // Set document straightening parameters for the scanning screen.
+            outputSettings.apply {
+                straighteningParameters = DocumentStraighteningParameters(
+                    straighteningMode = DocumentStraighteningMode.STRAIGHTEN,
+                    // Expected aspect ratios for the documents. Comment if unknown.
+                    aspectRatios = listOf(AspectRatio(3.0, 4.0))
+                )
+            }
+        }
+        // Start the recognizer activity.
+        documentScannerResult.launch(configuration)
+    }
+    // @EndTag("Set Document Straightening Parameters")
+
+}
+
diff --git a/document-scanner-ready-to-use-ui-example/build.gradle b/document-scanner-ready-to-use-ui-example/build.gradle
index e462db42..96bda803 100644
--- a/document-scanner-ready-to-use-ui-example/build.gradle
+++ b/document-scanner-ready-to-use-ui-example/build.gradle
@@ -1,5 +1,5 @@
 
 plugins {
-    id("com.android.application") version '8.9.0' apply false
+    id("com.android.application") version '8.9.1' apply false
     id("org.jetbrains.kotlin.android") version "2.2.21" apply false
 }
