quickcapture 1.0.11
quickcapture: ^1.0.11 copied to clipboard
QuickCapture AI Based Mobile Document Scanning plugin for Flutter From Extrieve.
example/lib/main.dart
import 'dart:convert';
import 'dart:io';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'dart:async';
import 'package:open_file/open_file.dart';
import 'package:fluttertoast/fluttertoast.dart';
import 'package:gallery_saver/gallery_saver.dart';
import 'package:image_picker/image_picker.dart';
//Import Quickcapture flutter plugin
import 'package:quickcapture/quickcapture.dart';
void main() {
runApp(const MyApp());
}
typedef MyCallback = void Function(String result);
class MyApp extends StatefulWidget {
const MyApp({super.key});
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
List<String> _capturedImage = [];
//final _quickcapturePlugin = Quickcapture();
final _quickcapturePlugin = Quickcapture();
@override
void initState() {
super.initState();
//Do license activation before initialisation (if license available - optional)
activateLicense();
//initalise plugin
_quickcapturePlugin.initialize();
}
Future<void> startCapture() async {
try {
//set configuration for current capture session
setConfigForCapture();
//Triger capture
String? response = await _quickcapturePlugin.startCapture();
if (response != null) {
setState(() {
Map<String, dynamic> jsonResponse = jsonDecode(response);
_capturedImage = List<String>.from(jsonResponse['fileCollection']);
});
// Save all images to the device gallery
for (String imagePath in _capturedImage) {
bool? success = await GallerySaver.saveImage(imagePath);
if (success == true) {
Fluttertoast.showToast(
msg: "Image saved to gallery: $imagePath",
backgroundColor: Colors.green,
textColor: Colors.white,
);
} else {
Fluttertoast.showToast(
msg: "Failed to save image: $imagePath",
backgroundColor: Colors.red,
textColor: Colors.white,
);
}
}
} else {
throw Exception("No response received from startCapture");
}
} catch (e) {
Fluttertoast.showToast(
msg: "Error capturing image: ${e.toString()}",
backgroundColor: Colors.red,
textColor: Colors.white,
);
}
}
Future<void> buildPDF() async {
String? response = await _quickcapturePlugin.buildPDFForLastCapture();
OpenFile.open(response);
}
Future<void> activateLicense() async {
String androidLicense = "<Pass license for android here>";
String iosLicense = "<Pass the license string for IOS here>";
bool? response = await _quickcapturePlugin.activateLicense(
android: androidLicense, ios: iosLicense);
String lisMsg = "License activation failed.Invalid license";
Color bgColor =
const Color.fromARGB(255, 216, 90, 58); // Use green for success
if (response != null && response == true) {
lisMsg = "License for android activated";
bgColor = const Color.fromARGB(255, 58, 216, 84);
}
Fluttertoast.showToast(
msg: lisMsg,
toastLength: Toast.LENGTH_SHORT,
gravity: ToastGravity.CENTER,
timeInSecForIosWeb: 1,
backgroundColor: bgColor,
textColor: Colors.white,
fontSize: 16.0);
}
void setConfigForCapture() {
// Modify configurations as needed
// _quickcapturePlugin.config.image
// .setImageQuality(ImageQuality.documentQuality);
_quickcapturePlugin.config.image.setDPI(DPI.dpi200);
_quickcapturePlugin.config.image
.setLayoutType(LayoutType.A4); // Set layout type
//refer documentation for all possible type
// _quickcapturePlugin.config.image
// .setResizeMode(ResizeMode.preserveAspectOnly);
_quickcapturePlugin.config.capture.enableFlash = true;
//_quickcapturePlugin.config.capture.captureSound = true;
_quickcapturePlugin.config.capture.maxPage = 2;
//Eg: set 2 for ID capture to capture both front and back secanrio
//_quickcapturePlugin.config.capture.cameraToggle =
// CameraToggleType.enableBackDefault;
//_quickcapturePlugin.config.capture.colorMode = ColorModes.rgb;
// _quickcapturePlugin.config.capture.bottomStampData =
// "Provide stamping to the bottom of images {DATETIME}";
}
Future<void> pickImageFromGallery() async {
final ImagePicker picker = ImagePicker();
try {
// Pick an image from the gallery
final XFile? pickedFile =
await picker.pickImage(source: ImageSource.gallery);
if (pickedFile != null) {
String imagePath = pickedFile.path;
if (kDebugMode) {
print("imagePath:$imagePath");
}
//Set image related custon config : based on set image config output image
//will optimsie and generate on compressToJPEG
// _quickcapturePlugin.config.image
// .setImageQuality(ImageQuality.documentQuality);
// _quickcapturePlugin.config.image.setDPI(DPI.dpi200);
//If resize mode to specify
_quickcapturePlugin.config.image
.setResizeMode(ResizeMode.fitWithAspect);
//If cutsom layout needed for compressed image do :
_quickcapturePlugin.config.image.setLayoutType(LayoutType.A4);
//If cutsom layout needed for compressed image do :
//_quickcapturePlugin.config.image.setCustomLayout(500, 900);
// Call the method in QuickcapturePlugin with the selected image path
String? compressedImagePath =
await _quickcapturePlugin.compressToJPEG(imagePath);
if (compressedImagePath != null && compressedImagePath.isNotEmpty) {
// Save the compressed image to the device gallery
bool? saved = await GallerySaver.saveImage(compressedImagePath);
if (saved == true) {
Fluttertoast.showToast(
msg:
"Image processed and saved successfully: $compressedImagePath",
backgroundColor: Colors.green,
textColor: Colors.white,
);
} else {
Fluttertoast.showToast(
msg: "Failed to save compressed image to gallery.",
backgroundColor: Colors.red,
textColor: Colors.white,
);
}
} else {
Fluttertoast.showToast(
msg: "Failed to compress the image.",
backgroundColor: Colors.red,
textColor: Colors.white,
);
}
} else {
Fluttertoast.showToast(
msg: "No image selected.",
backgroundColor: Colors.orange,
textColor: Colors.white,
);
}
} catch (e) {
Fluttertoast.showToast(
msg: "Error picking or processing image: ${e.toString()}",
backgroundColor: Colors.red,
textColor: Colors.white,
);
}
}
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('QuickCapture'),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
_capturedImage.isNotEmpty
? Expanded(
child: ImageGrid(_capturedImage),
)
: Container(),
ElevatedButton(
onPressed: () => startCapture(),
child: const Text("Start Capture"),
),
ElevatedButton(
onPressed: () => buildPDF(),
child: const Text("Build PDF For Last Capture"),
),
ElevatedButton(
onPressed: () => pickImageFromGallery(),
child: const Text("Attach from Gallery"), // New button
),
],
),
),
),
);
}
}
class ImageGrid extends StatelessWidget {
final List<String> imagePaths;
const ImageGrid(this.imagePaths, {super.key});
@override
Widget build(BuildContext context) {
return GridView.builder(
gridDelegate: const SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount: 3, // Number of images per row
crossAxisSpacing: 8.0,
mainAxisSpacing: 8.0,
),
itemCount: imagePaths.length,
itemBuilder: (context, index) {
return Image.file(
File(imagePaths[index]),
width: 200,
height: 200,
fit: BoxFit.contain,
);
},
);
}
}