flutter_image_compress 1.0.0-nullsafety copy "flutter_image_compress: ^1.0.0-nullsafety" to clipboard
flutter_image_compress: ^1.0.0-nullsafety copied to clipboard

outdated

compress image with native code(objc kotlin), it's faster. This library can work on android/ios.

example/lib/main.dart

import 'dart:async';
import 'dart:io';
import 'dart:math' as math;
import 'dart:typed_data';

import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_image_compress/flutter_image_compress.dart';
import 'package:path_provider/path_provider.dart' as path_provider;

import 'const/resource.dart';
import 'time_logger.dart';
// import 'package:image_picker/image_picker.dart';

void main() {
  runApp(new MyApp());
  FlutterImageCompress.showNativeLog = true;
}

class MyApp extends StatefulWidget {
  @override
  _MyAppState createState() => new _MyAppState();
}

class _MyAppState extends State<MyApp> {
  @override
  void initState() {
    super.initState();
  }

  // Platform messages are asynchronous, so we initialize in an async method.
  Future<void> compress() async {
    final img = AssetImage("img/img.jpg");
    print("pre compress");
    final config = new ImageConfiguration();

    AssetBundleImageKey key = await img.obtainKey(config);
    final ByteData data = await key.bundle.load(key.name);

    final beforeCompress = data.lengthInBytes;
    print("beforeCompress = $beforeCompress");

    final result =
        await FlutterImageCompress.compressWithList(data.buffer.asUint8List());

    print("after = ${result.length}");
  }

  ImageProvider? provider;

  @override
  Widget build(BuildContext context) {
    return new MaterialApp(
      home: new Scaffold(
        appBar: new AppBar(
          title: const Text('Plugin example app'),
        ),
        body: ListView(
          children: <Widget>[
            AspectRatio(
              child: Image(
                image: provider ?? AssetImage("img/img.jpg"),
                width: double.infinity,
                fit: BoxFit.contain,
              ),
              aspectRatio: 1 / 1,
            ),
            TextButton(
              child: Text('CompressFile and rotate 180'),
              onPressed: _testCompressFile,
            ),
            TextButton(
              child: Text('CompressAndGetFile and rotate 90'),
              onPressed: getFileImage,
            ),
            TextButton(
              child: Text('CompressAsset and rotate 135'),
              onPressed: () => testCompressAsset("img/img.jpg"),
            ),
            TextButton(
              child: Text('CompressList and rotate 270'),
              onPressed: compressListExample,
            ),
            TextButton(
              child: Text('test compress auto angle'),
              onPressed: _compressAssetAndAutoRotate,
            ),
            TextButton(
              child: Text('Test png '),
              onPressed: _compressPngImage,
            ),
            TextButton(
              child: Text('Format transparent PNG'),
              onPressed: _compressTransPNG,
            ),
            TextButton(
              child: Text('Restore transparent PNG'),
              onPressed: _restoreTransPNG,
            ),
            TextButton(
              child: Text('Keep exif image'),
              onPressed: _compressImageAndKeepExif,
            ),
            TextButton(
              child: Text('Convert to heic format and print the file url'),
              onPressed: _compressHeicExample,
            ),
            TextButton(
              child: Text('Convert to webp format, Just support android'),
              onPressed: _compressAndroidWebpExample,
            ),
          ],
        ),
        floatingActionButton: FloatingActionButton(
          child: Icon(Icons.computer),
          onPressed: () => setState(() => this.provider = null),
          tooltip: "show origin asset",
        ),
      ),
    );
  }

  Future<Directory> getTemporaryDirectory() async {
    return Directory.systemTemp;
  }

  void _testCompressFile() async {
    final img = AssetImage("img/img.jpg");
    print("pre compress");
    final config = new ImageConfiguration();

    AssetBundleImageKey key = await img.obtainKey(config);
    final ByteData data = await key.bundle.load(key.name);
    final dir = await path_provider.getTemporaryDirectory();
    print('dir = $dir');

    File file = createFile("${dir.absolute.path}/test.png");
    file.writeAsBytesSync(data.buffer.asUint8List());

    final result = await testCompressFile(file);

    if (result == null) return;

    ImageProvider provider = MemoryImage(result);
    this.provider = provider;
    setState(() {});
  }

  File createFile(String path) {
    final file = File(path);
    if (!file.existsSync()) {
      file.createSync(recursive: true);
    }

    return file;
  }

  Future<String> getExampleFilePath() async {
    final img = AssetImage("img/img.jpg");
    print("pre compress");
    final config = new ImageConfiguration();

    AssetBundleImageKey key = await img.obtainKey(config);
    final ByteData data = await key.bundle.load(key.name);
    final dir = await path_provider.getTemporaryDirectory();

    File file = createFile("${dir.absolute.path}/test.png");
    file.createSync(recursive: true);
    file.writeAsBytesSync(data.buffer.asUint8List());
    return file.absolute.path;
  }

  void getFileImage() async {
    final img = AssetImage("img/img.jpg");
    print("pre compress");
    final config = new ImageConfiguration();

    AssetBundleImageKey key = await img.obtainKey(config);
    final ByteData data = await key.bundle.load(key.name);
    final dir = await path_provider.getTemporaryDirectory();

    File file = createFile("${dir.absolute.path}/test.png");
    file.writeAsBytesSync(data.buffer.asUint8List());

    final targetPath = dir.absolute.path + "/temp.jpg";
    final imgFile = await testCompressAndGetFile(file, targetPath);

    if (imgFile == null) {
      return;
    }

    provider = FileImage(imgFile);
    setState(() {});
  }

  Future<Uint8List?> testCompressFile(File file) async {
    print("testCompressFile");
    final result = await FlutterImageCompress.compressWithFile(
      file.absolute.path,
      minWidth: 2300,
      minHeight: 1500,
      quality: 94,
      rotate: 180,
    );
    print(file.lengthSync());
    print(result?.length);
    return result;
  }

  Future<File?> testCompressAndGetFile(File file, String targetPath) async {
    print("testCompressAndGetFile");
    final result = await FlutterImageCompress.compressAndGetFile(
      file.absolute.path,
      targetPath,
      quality: 90,
      minWidth: 1024,
      minHeight: 1024,
      rotate: 90,
    );

    print(file.lengthSync());
    print(result?.lengthSync());

    return result;
  }

  Future testCompressAsset(String assetName) async {
    print("testCompressAsset");
    final list = await FlutterImageCompress.compressAssetImage(
      assetName,
      minHeight: 1920,
      minWidth: 1080,
      quality: 96,
      rotate: 135,
    );

    if (list == null) return;

    this.provider = MemoryImage(Uint8List.fromList(list));
    setState(() {});
  }

  Future compressListExample() async {
    final data = await rootBundle.load("img/img.jpg");

    final memory = await testComporessList(data.buffer.asUint8List());

    setState(() {
      this.provider = MemoryImage(memory);
    });
  }

  Future<Uint8List> testComporessList(Uint8List list) async {
    final result = await FlutterImageCompress.compressWithList(
      list,
      minHeight: 1080,
      minWidth: 1080,
      quality: 96,
      rotate: 270,
      format: CompressFormat.webp,
    );
    print(list.length);
    print(result.length);
    return result;
  }

  void writeToFile(List<int> list, String filePath) {
    final file = File(filePath);
    file.writeAsBytes(list, flush: true, mode: FileMode.write);
  }

  void _compressAssetAndAutoRotate() async {
    final result = await FlutterImageCompress.compressAssetImage(
      R.IMG_AUTO_ANGLE_JPG,
      minWidth: 1000,
      quality: 95,
      // autoCorrectionAngle: false,
    );

    if (result == null) return;

    final u8list = Uint8List.fromList(result);
    this.provider = MemoryImage(u8list);
    setState(() {});
  }

  void _compressPngImage() async {
    final result = await FlutterImageCompress.compressAssetImage(
      R.IMG_HEADER_PNG,
      minWidth: 300,
      minHeight: 500,
    );

    if (result == null) return;

    final u8list = Uint8List.fromList(result);
    this.provider = MemoryImage(u8list);
    setState(() {});
  }

  void _compressTransPNG() async {
    final bytes =
        await getAssetImageUint8List(R.IMG_TRANSPARENT_BACKGROUND_PNG);
    final result = await FlutterImageCompress.compressWithList(
      bytes,
      minHeight: 100,
      minWidth: 100,
      format: CompressFormat.png,
    );

    final u8list = Uint8List.fromList(result);
    this.provider = MemoryImage(u8list);
    setState(() {});
  }

  void _restoreTransPNG() async {
    this.provider = AssetImage(R.IMG_TRANSPARENT_BACKGROUND_PNG);
    setState(() {});
  }

  void _compressImageAndKeepExif() async {
    final result = await FlutterImageCompress.compressAssetImage(
      R.IMG_AUTO_ANGLE_JPG,
      minWidth: 500,
      minHeight: 600,
      // autoCorrectionAngle: false,
      keepExif: true,
    );

    if (result == null) return;

    this.provider = MemoryImage(Uint8List.fromList(result));
    setState(() {});

    // final dir = (await path_provider.getTemporaryDirectory()).path;
    // final f = File("$dir/tmp.jpg");
    // f.writeAsBytesSync(result);
    // print("f.path = ${f.path}");
  }

  void _compressHeicExample() async {
    print("start compress");
    final logger = TimeLogger();
    logger.startRecoder();
    final tmpDir = (await getTemporaryDirectory()).path;
    final target = "$tmpDir/${DateTime.now().millisecondsSinceEpoch}.heic";
    final srcPath = await getExampleFilePath();
    final result = await FlutterImageCompress.compressAndGetFile(
      srcPath,
      target,
      format: CompressFormat.heic,
      quality: 90,
    );

    if (result == null) return;

    print("Compress heic success.");
    logger.logTime();
    print("src, path = $srcPath length = ${File(srcPath).lengthSync()}");
    print(
        "Compress heic result path: ${result.absolute.path}, size: ${result.lengthSync()}");
  }

  void _compressAndroidWebpExample() async {
    // Android compress very nice, but the iOS encode UIImage to webp is slow.
    final logger = TimeLogger();
    logger.startRecoder();
    print("start compress webp");
    final quality = 90;
    final tmpDir = (await getTemporaryDirectory()).path;
    final target =
        "$tmpDir/${DateTime.now().millisecondsSinceEpoch}-$quality.webp";
    final srcPath = await getExampleFilePath();
    final result = await FlutterImageCompress.compressAndGetFile(
      srcPath,
      target,
      format: CompressFormat.webp,
      minHeight: 800,
      minWidth: 800,
      quality: quality,
    );

    if (result == null) return;

    print("Compress webp success.");
    logger.logTime();
    print("src, path = $srcPath length = ${File(srcPath).lengthSync()}");
    print(
        "Compress webp result path: ${result.absolute.path}, size: ${result.lengthSync()}");

    provider = FileImage(result);
    setState(() {});
  }
}

Future<Uint8List> getAssetImageUint8List(String key) async {
  final byteData = await rootBundle.load(key);
  return byteData.buffer.asUint8List();
}

double calcScale({
  required double srcWidth,
  required double srcHeight,
  required double minWidth,
  required double minHeight,
}) {
  final scaleW = srcWidth / minWidth;
  final scaleH = srcHeight / minHeight;

  final scale = math.max(1.0, math.min(scaleW, scaleH));

  return scale;
}
1555
likes
0
pub points
100%
popularity

Publisher

verified publisherfluttercandies.com

compress image with native code(objc kotlin), it's faster. This library can work on android/ios.

Repository (GitHub)
View/report issues

License

unknown (license)

Dependencies

flutter

More

Packages that depend on flutter_image_compress