PackageTrack
Sign in Get early access

cunning_document_scanner

A document scanner plugin for flutter. Scan and crop automatically on iOS and Android.

3.0.1 53K downloads/mo #1440 most downloaded on pub.dev vicajilau/cunning_document_scanner

What this package is like to depend on

Last release 13 days ago

11 Aug 2026

Release timing varies

gaps range from 9 days to 1.1 years

Nearly every release is documented

notes for 27 of 27 stable releases

Nothing withdrawn

no release was ever pulled

5 years old

27 releases · first in 2022

11 releases in the last 12 months

see the full history below

Release timeline

27 releases · Feb 2022 to Aug 2026
2023 2024 2025 2026
Release Pre-release

Releases

latest 27
  1. 3.0.1 11 Aug 2026
    Release notes

    What's Changed

    • fix(android): raise minSdk to 24, the lowest level actually reachable by @vicajilau in #164
    • fix(android): make cleanCache() cover files the GMS scanner produces by @vicajilau in #165

    Full Changelog: v3.0.0...v3.0.1

    Open source →
    Release notes

    Changed

    • The Android minSdk is now 24, up from the 21 previously declared. 21 was never a level a host application could reach: Flutter's Gradle plugin fails the build below API 23, and play-services-mlkit-document-scanner declares 23 in its own manifest. 24 is Flutter's own default minSdkVersion, so a project that has not overridden it needs no change. Applications pinned to API 23 are the exception — they built and ran before and will now fail the manifest merge, and must either raise their minSdk to 24 or stay on 3.0.0. The README documented the unreachable 21 and has been corrected everywhere it appeared.

    Fixed

    • cleanCache() removed nothing on most Android devices. The GMS/ML Kit document scanner is the primary Android path, and it writes its page images and PDFs under its own naming scheme rather than this plugin's DOCUMENT_SCAN_ prefix, so cleanCache() never matched or removed them even though the plugin had returned those exact paths to Flutter as its own output. Each file is now copied into the plugin's own prefixed storage before its path is returned.
    Open source →
  2. 3.0.0 11 Aug 2026
    Release notes

    What's Changed

    • chore(deps): bump cunning_document_scanner from 2.7.0 to 2.8.0 in /example by @dependabot[bot] in #155
    • chore(deps): bump actions/setup-java from 5 to 5.6.0 by @dependabot[bot] in #156
    • chore(deps): bump actions/setup-java from 5.6.0 to 5.7.0 by @dependabot[bot] in #159
    • 3.0.0: fix cleanCache data loss, repair Android gallery import, drop permission_handler by @vicajilau in #160
    • Fix result callback leaks that could lock the scanner, and cleanCache's Activity requirement by @vicajilau in #161
    • Downsample images in the Android fallback scanner, and stop claiming it detects corners by @vicajilau in #162
    • fix(ios): stop the Camera/Gallery action sheet from dropping the scan result by @vicajilau in #163

    Full Changelog: v2.8.0...v3.0.0

    Open source →
    Release notes

    [!IMPORTANT] This release changes where scanned files are written and how cancellation is reported. Read the breaking changes below before upgrading.

    Breaking changes

    • permission_handler is no longer a dependency. The iOS camera permission is now requested natively through AVCaptureDevice, which is exactly the API permission_handler wrapped for Permission.camera. If your app imports package:permission_handler without declaring it in your own pubspec.yaml — relying on it arriving transitively through this plugin — add it explicitly:
      flutter pub add permission_handler
      
      Nothing else changes: permission refusals still throw CunningDocumentScannerException with code: 'permission_denied' and the same message. Apps that already declare permission_handler are unaffected.
    • iOS output moved out of the Documents directory. Scans and generated PDFs are now written to a private Library/Caches/cunning_document_scanner/ subdirectory. The returned paths are still absolute and readable, but the files are no longer backed up to iCloud and may be reclaimed by the system. Copy anything you need to keep to your own storage.
    • getPictures() now returns null on cancellation on every platform. Android previously returned an empty list, contradicting the documented contract. Empty native results are normalized to null.
    • Native errors are reported as CunningDocumentScannerException. getPictures() and cleanCache() no longer leak PlatformException; the platform error code is preserved in CunningDocumentScannerException.code.
    • androidScannerMode is no longer nullable. It defaults to AndroidScannerMode.full; remove any explicit null.
    • IosScannerOptions is no longer a const constructor. It now validates jpgCompressionQuality and throws an ArgumentError for values outside 0.0 - 1.0.

    Fixed

    • Importing images from the gallery could fail on Android. Providers that keep images in the cloud, such as Google Photos, return a URI before the bytes are available locally. The cropper opened that stream on the main thread as soon as it started, freezing the UI for the length of the download and aborting with a decode error when the image was not ready yet. Image reading, decoding and cropping now run on a background thread with a progress indicator, and an image that genuinely cannot be read reports that it may still be downloading.
    • Large images could exhaust memory in the Android fallback scanner. Photos were decoded at full resolution, and rotating one by its EXIF orientation allocated a second copy without releasing the first, so a 12 MP capture peaked at roughly 96 MB. Images are now downsampled to a longest edge of 2048 px and the intermediate bitmap is recycled. This path runs on devices without Google Play Services, which are the least able to absorb that. The gallery import was routed through the same decoder so crop coordinates stay in one coordinate space.
    • The scanner could be locked out for the rest of the process on iPad. The cameraAndGallery action sheet is a popover there, and dismissing it by tapping outside could leave the pending result callback stranded, after which every later call failed with ALREADY_ACTIVE. The same happened when no view controller was available to present from. Dismissal by gesture is now treated as a cancellation, and a missing presenter fails immediately with NO_VIEW_CONTROLLER rather than consuming the call.
    • cleanCache() no longer requires an attached Activity on Android. It only ever needed a Context, so cleaning at startup — before any Activity is attached — used to fail with NO_ACTIVITY for no technical reason.
    • A restricted camera authorization was ignored on iOS. Devices under parental controls or an MDM policy report restricted, which the Dart-side check did not treat as a refusal, so the scanner opened a camera the user could never grant access to. The native check covers it.
    • The camera permission was requested even for gallery-only flows. ScannerSource.gallery uses the out-of-process system photo picker, which needs no permission; it no longer prompts for anything.
    • cleanCache() could delete host application data. On iOS it removed every .pdf, .jpg and .png in the app's Documents directory; on Android it matched by file extension in cacheDir and the pictures directory. Both now delete only files the plugin itself wrote, identified by the DOCUMENT_SCAN_ prefix and the private storage directory.
    • Android gallery multi-selection was broken. The picker requested multiple selection but only read Intent.data, so selecting more than one image reported "No image selected". Selections are now read from clipData and every image is cropped in sequence.
    • Android gallery imports ignored noOfPages, hardcoding a single page.
    • Concurrent getPictures() calls no longer orphan the first call's Future; the second call fails fast with an ALREADY_ACTIVE error.
    • Calling the plugin while detached from an Activity returns a NO_ACTIVITY error instead of crashing with UninitializedPropertyAccessException.
    • iOS image write failures are surfaced as errors instead of returning paths to files that were never created.
    • Removed the leftover Huawei com.huawei.hms.ml.DEPENDENCY manifest entry, which was still being merged into every host application after HMS support was dropped in 2.6.0.

    Added

    • IosScannerOptions.defaultFilter and IosScannerOptions.showFilterBar expose the iOS cropper filters (IosDocumentFilter.original, .color, .grayscale, .blackAndWhite) to Dart.
    • Kotlin unit tests for the method channel argument helpers, run in CI.
    • tool/check_versions.sh, run in CI, fails the build when pubspec.yaml, the podspec, android/build.gradle.kts and the changelog disagree on the version.
    • Documented how to customize the native UI. An application can override any of the plugin's text, and on Android also its colors and dimensions, by redeclaring the matching resource name — cunning_* on Android, cunning_document_scanner_* in Localizable.strings on iOS. This already worked, since the plugin resolves each name against the host application first, but was never written down. iOS colors remain hard-coded and are not overridable.

    Changed

    • Removed the unconditional debug logging from the Android plugin and the debug print from the Dart layer; both leaked file paths and URIs into release logs.
    • plugin_platform_interface moved to dev_dependencies; it was only ever used by tests.
    • Added topics and issue_tracker to pubspec.yaml.
    • Stricter analysis (strict-casts, strict-raw-types, public_member_api_docs) and raised, rather than disabled, the SwiftLint size and complexity rules.
    • The Android fallback cropper shows a page counter while working through a batch of imported images, matching what iOS already displayed.
    • Android is localized. Its strings shipped in English only while iOS carried 29 languages; both platforms now cover the same set. The shared wording is taken from the existing iOS translations so the two say the same thing.
    • Added Basque (eu) and Galician (gl) on both platforms, bringing the total to 31. Catalan was already supported. Valencian is served by the Catalan localization, and Asturian, Aragonese and Aranese are left out because iOS does not offer them as system languages.
    • Every Android resource is now prefixed cunning_. A library's resources are merged into the host application's resource table and the application wins any name collision, so the plugin previously exposed 45 unprefixed names — including black, image_view and activity_image_crop — that an application could silently override, restyling or breaking the scanner. resourcePrefix = "cunning_" makes AGP flag any future lapse, and the convention is documented in the README. These are internal resources, so applications need no changes.
    • Removed the unused EdgeDetector interface, and corrected documentation that claimed the fallback scanner detects corners automatically. It does not, and never did: the crop quad starts as a fixed inset that the user positions. Automatic detection comes from ML Kit on Android and Vision on iOS.
    • Documented that noOfPages is applied after the fact by the iOS document camera, which exposes no page limit of its own.
    Open source →
  3. 2.8.0 25 Jul 2026
    Release notes

    What's Changed

    • chore(deps): bump actions/setup-java from 4 to 5 by @dependabot[bot] in #152
    • feat(ios): add document image filters to custom cropper (closes #153) by @vicajilau in #154

    Full Changelog: v2.7.0...v2.8.0

    Open source →
    Release notes

    iOS

    • Added document image filter options (Original, Color, Grayscale, B&W) to the custom document cropper (CunningDocumentCropperViewController) when importing images from the gallery, achieving feature parity with Android ML Kit (fixes #153).
    Open source →
  4. 2.7.0 21 Jul 2026
    Release notes

    What's Changed

    • chore(deps): bump cunning_document_scanner from 2.5.1 to 2.6.0 in /example by @dependabot[bot] in #148
    • feat(ios): implement manual cropping for gallery images by @vicajilau in #150
    • Add cleanCache method and enforce iOS page limit with SwiftLint CI by @vicajilau in #151

    Full Changelog: v2.6.0...v2.7.0

    Open source →
    Release notes

    General

    • Added CunningDocumentScanner.cleanCache() to clear temporary scanned images and generated PDF files from local storage.
    • Enforced noOfPages page limit validation in Dart (noOfPages > 0), throwing an ArgumentError when invalid values are supplied.
    • Documented exception handling for ArgumentError and CunningDocumentScannerException in DartDoc comments and README.md.

    iOS

    • Added manual document cropper for gallery-imported images (ScannerSource.gallery), resolving the limitation where gallery images could not be manually cropped before export.
    • Implemented noOfPages limit handling in both PHPickerViewController selection limit and VNDocumentCameraViewController.
    • Implemented native cleanCache support.
    • Implemented a circular MagnifierView precision zoom lens centered over handles during touch dragging, providing pixel-perfect corner positioning.
    • Added a cancel confirmation dialog to prevent accidental data loss in multi-page scanning.
    • Fixed rotate button behavior to properly map cropping coordinates 90 degrees clockwise without losing user progress.
    • Optimized image loading and processing:
      • Offloaded heavy image orientation fixes (fixedOrientation()) and perspective correction filters to background threads.
      • Wrapped background processing calls in autoreleasepool blocks to force immediate memory deallocation and avoid OOM crashes.
      • Downscaled imported gallery images to a maximum of 2048px on load to prevent concurrent memory spikes.
      • Replaced CPU-intensive rotation with instant metadata orientation changes.
    • Added translations for the new cropper discard options across all 29 localized languages.

    Android

    • Implemented native cleanCache support purging DOCUMENT_SCAN_ files from cacheDir and PICTURES directory.
    Open source →
  5. 2.6.0 09 Jul 2026
    Release notes

    What's Changed

    • fix(android): make HMS ML Kit dependencies optional to resolve allowBackup conflict by @vicajilau in #145

    Full Changelog: v2.5.0...v2.6.0

    Open source →
    Release notes

    Android

    • Removed HMS (Huawei Mobile Services) support entirely to ensure 16 KB page-size compatibility on Android 15+ (fixes #146).
    • Replaced deprecated getParcelable(key) with type-safe androidx.core.os.BundleCompat.getParcelable for Android 13+ compatibility.
    • Migrated the legacy android block to the modern configure<LibraryExtension> block and updated conditional Kotlin plugin application in build.gradle.kts to resolve build/deprecation warnings.
    • Removed redundant and deprecated sourceSets block, as Kotlin source directories are resolved automatically by Gradle.
    Open source →
  6. 2.5.0 02 Jul 2026
    Release notes

    What's Changed

    • feat(android): add HMS ML Kit document edge detection and fix GMS+HMS dual-service loop by @vicajilau in #143

    Full Changelog: v2.4.0...v2.5.0

    Open source →
    Release notes

    General

    • Introduced ScannerSource enum to specify the source of document images: camera, gallery, or cameraAndGallery.
    • Deprecated isGalleryImportAllowed in favor of scannerSource. If scannerSource is provided, it takes precedence and isGalleryImportAllowed is ignored.

    Android

    • Added automatic document edge detection for Huawei Mobile Services (HMS) devices using HMS ML Kit Document Skew Correction.
    • Fixed a crash/restart loop issue on older GMS+HMS dual-service devices (such as Honor 8X and Huawei P30 Lite) by bypassing GMS and launching the fallback scanner directly on HMS-enabled devices.
    • Added direct gallery selection support. When ScannerSource.gallery is chosen, the system launches the device's image picker and routes the selected image directly to the fallback crop editor (DocumentScannerActivity) for edge adjustment and perspective correction.

    iOS

    • Integrated direct gallery picker navigation. When ScannerSource.gallery is chosen, the plugin opens the native photo library (PHPickerViewController) directly, bypassing the alert/choice menu.
    Open source →
  7. 2.4.0 30 Jun 2026
    Release notes

    What's Changed

    • Bump cunning_document_scanner from 2.2.0 to 2.3.0 in /example by @dependabot[bot] in #138
    • Feature/build in kotlin migration issue by @daniJimen in #139
    • Refactor: remove redundant camera and storage permissions from Android by @vicajilau in #140
    • feat: add support for PDF export in document scanning across platforms by @vicajilau in #141
    • Feature: add native gallery import support on iOS by @vicajilau in #142

    New Contributors

    Full Changelog: v2.3.0...v2.4.0

    Open source →
    Release notes

    General

    • Added cross-platform support for native PDF export. Call CunningDocumentScanner.getPictures(asPdf: true) to return a list containing a single path pointing to the generated PDF.

    Android

    • Removed redundant camera and storage permissions from AndroidManifest.xml.
    • Android no longer prompts the user for camera or storage permissions at runtime since ML Kit and the fallback camera intent handle them without requiring permission in the host app.
    • Integrated native PDF support in both the Google Play Services ML Kit Document Scanner and the local low-RAM fallback scanner (using built-in PdfDocument).
    • Migrated to "Built-in Kotlin" support, removing manual Kotlin Gradle Plugin (KGP) application for future Flutter compatibility.
    • Updated Gradle wrapper to 8.14.5.
    • Updated Android Gradle Plugin (AGP) to 8.13.1.
    • Updated Kotlin version to 2.2.21.

    iOS

    • Camera permission request remains active and required for iOS VisionKit.
    • Integrated native PDF compilation using PDFKit (converting VisionKit scan pages into a single PDF document).
    • Added native support for isGalleryImportAllowed on iOS. Users can now choose to scan using the camera (VisionKit) or import existing documents from their photo library (PHPickerViewController on iOS 14+ supporting multi-selection, and UIImagePickerController on iOS 13). Imported images undergo the same native PDF/image conversion pipeline.
    • Added native localization support supporting 29 major languages for the iOS source selection Action Sheet and VisionKit interface. Included explicit color themes using KVC to guarantee text visibility across custom dark/light themes.
    Open source →
  8. 2.3.0 22 Jun 2026
    Release notes

    Full Changelog: v2.2.0...v2.3.0

    Open source →
    Release notes

    Android

    • Upgraded Gradle wrapper to version 8.14.5.
    • Modernized Kotlin configuration to use the new compilerOptions DSL instead of legacy kotlinOptions.
    • Cleaned up legacy build script configurations, removing deprecated dependencies (kotlin-stdlib-jdk7) and applying standard Kotlin DSL configurations.
    Open source →
  9. 2.2.0 22 Jun 2026
    Release notes

    What's Changed

    New Contributors

    Full Changelog: v2.1.0...v2.2.0

    Open source →
    Release notes

    Android

    • Added support for configuring the ML Kit document scanner mode.
    • Added AndroidScannerMode enum (full, base, baseWithFilter) to choose between different scanning pipelines.
    Open source →
  10. 2.1.0 22 Jun 2026
    Release notes

    What's Changed

    • feat: Major update to version 2.0.0 with improved exception handling … by @vicajilau in #120
    • Bump cupertino_icons from 1.0.8 to 1.0.9 in /example by @dependabot[bot] in #129
    • Bump path_provider from 2.1.5 to 2.1.6 in /example by @dependabot[bot] in #133
    • Migrate iOS plugin to Swift Package Manager by @olekeke999 in #134

    New Contributors

    Full Changelog: v1.4.0...v2.1.0

    Open source →
    Release notes

    General

    • Bumped Dart SDK constraint to >=3.5.0 <4.0.0.
    • Bumped Flutter SDK constraint to >=3.24.0.
    • Upgraded permission_handler to ^12.0.3.
    • Upgraded flutter_lints constraint to ^6.0.0.
    • Moved permission_handler_platform_interface to dev_dependencies.
    • Modernized Flutter code syntax.
    • Added launch configurations for VS Code.

    iOS

    • Migrated the iOS plugin to Swift Package Manager (SPM) for modern Flutter integration.
    • Reorganized the iOS directory structure under ios/cunning_document_scanner/ and added Package.swift.
    • Renamed SwiftCunningDocumentScannerPlugin to CunningDocumentScannerPlugin.
    Open source →
  11. 1.4.0 01 Dec 2025
    Release notes

    General

    • Bumped permission_handler to 12.0.1.
    • Updated the example app to use Kotlin 2.2.21, Android Gradle Plugin 8.13.1, and Gradle 8.13.
    • Added detailed documentation comments to the CunningDocumentScanner class.

    Android

    • Upgraded play-services-mlkit-document-scanner to 16.0.0.
    • Updated compileSdk to 34.
    Open source →
  12. 1.3.1 31 Jul 2025
    Release notes
    • Upgraded dependencies.
    Open source →
  13. 1.2.3 20 Jun 2024
    Release notes
    • Fix iOS crash where Documentscanner is not available
    Open source →
  14. 1.2.2 20 Apr 2024
    Release notes
    • Fix bitmap exception crash on Android (thanks to rosenberg_ptr)
    Open source →
  15. 1.2.1 06 Mar 2024
    Release notes
    • Add fallback for Android devices < 1.7GB RAM
    Open source →
  16. 1.2.0 28 Feb 2024
    Release notes
    • Use ML kit on Android
    • dropped nocrop support
    • image quality dropped
    Open source →
  17. 1.1.5 21 Feb 2024
    Release notes
    • Nmed parameters
    • crop default is false
    • dependencies updated
    • min ios version 12 now
    Open source →
  18. 1.1.4 07 Nov 2023
    Release notes
    • Fixed iOS permission issue in example
    • upgraded permission_handler
    Open source →
  19. 1.1.3 03 Nov 2023
    Release notes
    • Fixed permanently denied permission issue
    • Merged crop option for android - Thanks Edwin
    Open source →
  20. 1.1.2 08 Nov 2022
    Release notes
    • iOS return unique filenames
    Open source →
  21. 1.1.1 08 Nov 2022
    Release notes
    • Updated android documentscanner library
    Open source →
  22. 1.1.0 01 Oct 2022
    Release notes
    • Exchanged android documentscanner with https://github.com/WebsiteBeaver/android-document-scanner
    Open source →
  23. 1.0.4 19 Aug 2022
    Release notes
    • Fixed conflicting requestcodes issue
    Open source →
  24. 1.0.3 18 Aug 2022
    Release notes
    • Updated permission handler constraint to ^10
    • Android fixed nullsafe access issues
    Open source →
  25. 1.0.2 08 May 2022
    Release notes
    • Cleanup code - added images to README.md
    Open source →
  26. 1.0.1 05 May 2022
    Release notes
    • Fixed Playstore issue exported activity. Added documentation.
    Open source →
  27. 1.0.0 01 Feb 2022
    Release notes
    • Android and iOs Documentscanner based on Visionkit and AndroidDocument https://github.com/mayuce/AndroidDocumentScanner
    Open source →

Every package, every release, already written down.

The archive is open and free. Watching your own project is what we are building next.

Browse the archive