How to Open Image with Image Picker, Crop and Save in Flutter

In this example, we are going to make an image picker to open an image, crop it and save it again to the local storage gallery. Image cropper has aspect ratio, rotation, and more. see the example:

First of all, add imae_picker, image_cropper, image_gallery_saver flutter package by adding the following lines in pubspec.yaml file.

dependencies:
  flutter:
    sdk: flutter
  image_picker: ^0.8.4+4
  image_cropper: ^1.4.1
  image_gallery_saver: ^1.7.1

Add android:requestLegacyExternalStorage="true" on <application> tag in AndroidManifest.xml file.

<application
        android:requestLegacyExternalStorage="true"

Add These lines too on AndroidManifest.xml file inside <application> tag:

<application
    android:label="testapp"
    android:icon="@mipmap/ic_launcher">

    <activity
      android:name="com.yalantis.ucrop.UCropActivity"
      android:screenOrientation="portrait"
      android:theme="@style/Theme.AppCompat.Light.NoActionBar"/>

Import This on Script:

import 'dart:io';
import 'dart:typed_data';

final ImagePicker imgpicker = ImagePicker();
String imagepath = "";
late File imagefile; 

Import Image Picker package in your script:

import 'package:image_picker/image_picker.dart';
try {
  var pickedFile = await imgpicker.pickImage(source: ImageSource.gallery);
  //you can use ImageCourse.camera for Camera capture
  if(pickedFile != null){
      imagepath = pickedFile.path;
      imagefile = File(imagepath);
      setState(() {
      
      });
  }else{
      print("No image is selected.");
  }
}catch (e) {
  print("error while picking file.");
}

Import image_cropper package in your script:

import 'package:image_cropper/image_cropper.dart';
File? croppedfile = await ImageCropper.cropImage(
  sourcePath: imagepath,
  aspectRatioPresets: [
    CropAspectRatioPreset.square,
    CropAspectRatioPreset.ratio3x2,
    CropAspectRatioPreset.original,
    CropAspectRatioPreset.ratio4x3,
    CropAspectRatioPreset.ratio16x9
  ],
  androidUiSettings: AndroidUiSettings(
      toolbarTitle: 'Image Cropper',
      toolbarColor: Colors.deepPurpleAccent,
      toolbarWidgetColor: Colors.white,
      initAspectRatio: CropAspectRatioPreset.original,
      lockAspectRatio: false),
  iosUiSettings: IOSUiSettings(
    minimumAspectRatio: 1.0,
  )
);

if (croppedfile != null) {
    imagefile = croppedfile;
    setState(() { });
}else{
    print("Image is not cropped.");
}

Import image_gallery_saver package in your script:

import 'package:image_gallery_saver/image_gallery_saver.dart';
Uint8List bytes = await imagefile.readAsBytes();
var result = await ImageGallerySaver.saveImage(
          bytes,
          quality: 60,
          name: "new_mage.jpg"
      );
print(result);
if(result["isSuccess"] == true){
    print("Image saved successfully.");
}else{
    print(result["errorMessage"]);
}

import 'dart:io';
import 'dart:typed_data';

import 'package:flutter/material.dart';
import 'package:image_cropper/image_cropper.dart';
import 'package:image_gallery_saver/image_gallery_saver.dart';
import 'package:image_picker/image_picker.dart';

void main() {
  runApp( MaterialApp(
       home: Home()
  ));
}

class Home extends  StatefulWidget {
  @override
  State<Home> createState() => _HomeState();
}

class _HomeState extends State<Home> {

  final ImagePicker imgpicker = ImagePicker();
  String imagepath = "";
  late File imagefile; 
  
  openImage() async {
    try {
        var pickedFile = await imgpicker.pickImage(source: ImageSource.gallery);
        //you can use ImageCourse.camera for Camera capture
        if(pickedFile != null){
            imagepath = pickedFile.path;
            imagefile = File(imagepath);
            setState(() {
            
            });
        }else{
           print("No image is selected.");
        }
    }catch (e) {
        print("error while picking file.");
    }
  }

  cropImage() async {
    File? croppedfile = await ImageCropper.cropImage(
        sourcePath: imagepath,
        aspectRatioPresets: [
          CropAspectRatioPreset.square,
          CropAspectRatioPreset.ratio3x2,
          CropAspectRatioPreset.original,
          CropAspectRatioPreset.ratio4x3,
          CropAspectRatioPreset.ratio16x9
        ],
        androidUiSettings: AndroidUiSettings(
            toolbarTitle: 'Image Cropper',
            toolbarColor: Colors.deepPurpleAccent,
            toolbarWidgetColor: Colors.white,
            initAspectRatio: CropAspectRatioPreset.original,
            lockAspectRatio: false),
        iosUiSettings: IOSUiSettings(
          minimumAspectRatio: 1.0,
        )
      );

      if (croppedfile != null) {
          imagefile = croppedfile;
          setState(() { });
      }else{
         print("Image is not cropped.");
      }
  }
  
  @override
  Widget build(BuildContext context) {
    return Scaffold(
         resizeToAvoidBottomInset: false,
         appBar: AppBar(
            title: Text("Open Image, Crop and Save"),
            backgroundColor: Colors.deepPurpleAccent,
         ),
          body: Container(
             margin: EdgeInsets.only(top:30),
             alignment: Alignment.center,
             padding: EdgeInsets.all(20),
             child: Column(
               children: [

                  imagepath != ""?Image.file(imagefile):
                    Container( 
                      child: Text("No Image selected."),
                    ),
                  

                   Row( 
                     mainAxisAlignment: MainAxisAlignment.spaceBetween,
                     children: [
                       
                       //open button ----------------
                       ElevatedButton(
                          onPressed: (){
                              openImage();
                          }, 
                          child: Text("Open Image")
                        ),

                       //crop button --------------------
                        imagepath != ""? ElevatedButton(
                          style: ElevatedButton.styleFrom(primary: Colors.redAccent),
                          onPressed: (){
                              cropImage();
                          }, 
                          child: Text("Crop Image")
                        ): Container(),

                        //save button -------------------
                         imagepath != ""? ElevatedButton(
                          onPressed: () async {
                            Uint8List bytes = await imagefile.readAsBytes();
                            var result = await ImageGallerySaver.saveImage(
                                      bytes,
                                      quality: 60,
                                      name: "new_mage.jpg"
                                  );
                            print(result);
                            if(result["isSuccess"] == true){
                               print("Image saved successfully.");
                            }else{
                               print(result["errorMessage"]);
                            }
                          }, 
                          child: Text("Save Image")
                        ): Container(),

                        
                     ],


                   )
               ],
             ),
          )
      );
  }
}

App screen at the start:

Screenshot when Image is opened:

Screenshot While Cropping Image:

Saved Image in Local Gallery:

In this way, you can make an image picker to pick an image file, crop it and save it to the local storage gallery in the Flutter app.

No any Comments on this Article


Please Wait...