Flutter图片裁剪插件crop_box的使用

发布于 1周前 作者 nodeper 来自 Flutter

Flutter 图片裁剪插件 crop_box 的使用

背景

背景:为什么开发此组件?目前,我们在 flitter 应用中使用了视频合成技术,这涉及视频或图片素材的裁剪。当前市场上常见的组件大多基于图片,并且基本上使用 canvas 进行渲染和裁剪,这不符合我们的业务需求,因此我们需要自行开发一个裁剪组件。

中文文档

中文文档

示例

示例

需求分析

在需求设计之初,考虑到手势习惯并参考大多数编辑工具,定义了以下需求:

  • 裁剪框 固定 在屏幕上的某个位置。可以通过 单指拖动双指缩放 来调整素材的位置和大小以框选裁剪范围。
  • 素材的最小边长不能小于裁剪框对应边长,即裁剪框只能相对地在素材范围内移动。
  • 支持的素材类型包括 图片和视频

参数

名称 类型 描述 默认值
cropRect Rect 如果未填写初始裁剪区域,则会默认填充并居中,类似于 cover -
clipSize Size 要裁剪的素材大小 必填
cropRatio Size 裁剪框比例,默认为 16:9 Size(16, 9)
child Widget 要裁剪的素材 必填
maxCropSize Size 当前缩放状态下裁剪框的最大宽高,主要用于主动调整裁剪框大小。如果没有特殊要求,可以不配置 根据父组件计算
maxScale Double 允许放大的最大尺寸 10.0
needInnerBorder bool 是否需要在方形模式下内边框装饰(如果有圆角则不会显示) false
cropBoxType CropBoxType 裁剪框样式,默认为方形,可以改为圆形。如果是圆形,则 CropRatio 设置的值将无效,强制为 1:1 CropBoxType.Square
gridLine GridLine 裁剪网格线 -
backgroundColor Color 背景色 Color(0xff141414)
maskColor Color 掩膜色 Color.fromRGBO(0, 0, 0, 0.5)
cropBoxBorder CropBoxBorder 裁剪框样式,包括颜色、宽度和圆角信息 cropBoxBorder.width = 2
cropBoxBorder.color = Colors.white
cropBoxBorder.radius = Radius.circular(0)
cropRectUpdateStart Function 开始改变裁剪区域时的回调函数 -
cropRectUpdate Function(Rect rect) 裁剪区域变化时的回调函数 -
cropRectUpdateEnd Function(Rect rect) 结束裁剪区域变化时的回调函数 必填

示例代码

import 'package:crop_box/crop_box.dart';

// ...

CropBox(
  // cropRect: Rect.fromLTRB(1 - 0.4083, 0.162, 1, 0.3078), // 2.4倍 随机位置
  // cropRect: Rect.fromLTRB(0, 0, 0.4083, 0.1457), //2.4倍,都是0,0
  cropRect: Rect.fromLTRB(0, 0, 1, 0.3572), // 1倍
  clipSize: Size(200, 315),
  cropRatio: Size(16, 9),
  cropRectUpdateEnd: (rect) {
    print("裁剪区域最终位置: $rect");
  },
  cropRectUpdate: (rect) {
    print("裁剪区域变化: $rect");
  },
  child: Image.network(
    "https://img1.maka.im/materialStore/beijingshejia/tupianbeijinga/9/M_7TNT6NIM/M_7TNT6NIM_v1.jpg",
    width: double.infinity,
    height: double.infinity,
    fit: BoxFit.cover,
    loadingBuilder: (BuildContext context, Widget child, ImageChunkEvent loadingProgress) {
      if (loadingProgress == null)
        return child;
      return Center(
        child: CircularProgressIndicator(
          value: loadingProgress.expectedTotalBytes != null
              ? loadingProgress.cumulativeBytesLoaded / loadingProgress.expectedTotalBytes
              : null,
        ),
      );
    },
  ),
)

实际图像裁剪

你可以使用 ImageCrop.getResult 获取实际的图像字节。

/// 获取原始图像的 uint8List
Uint8List bytes = (await NetworkAssetBundle(Uri.parse(imageUrl)).load(imageUrl)).buffer.asUint8List();

/// 获取结果 uint8List
Uint8List result = await ImageCrop.getResult(
  clipRect: _resultRect, 
  image: bytes
);

更多关于Flutter图片裁剪插件crop_box的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html

1 回复

更多关于Flutter图片裁剪插件crop_box的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


当然,以下是一个关于如何在Flutter项目中使用crop_box插件进行图片裁剪的示例代码。crop_box是一个流行的图片裁剪插件,它允许用户在Flutter应用中手动选择裁剪区域。

首先,确保你的pubspec.yaml文件中已经添加了crop_box依赖项:

dependencies:
  flutter:
    sdk: flutter
  crop_box: ^0.2.0  # 请检查最新版本号

然后运行flutter pub get来安装依赖。

接下来,我们编写一个示例代码来展示如何使用crop_box进行图片裁剪。

import 'package:flutter/material.dart';
import 'package:image_picker/image_picker.dart';
import 'package:crop_box/crop_box.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Crop Box Example',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: MyHomePage(),
    );
  }
}

class MyHomePage extends StatefulWidget {
  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  File? _imageFile;
  File? _croppedImageFile;

  final ImagePicker _picker = ImagePicker();

  Future<void> _pickImage() async {
    final pickedFile = await _picker.pickImage(source: ImageSource.gallery);

    if (pickedFile != null) {
      setState(() {
        _imageFile = File(pickedFile.path);
      });
    }
  }

  Future<void> _cropImage() async {
    if (_imageFile == null) return;

    final croppedFile = await Navigator.push(
      context,
      MaterialPageRoute<File?>(
        builder: (context) => CropBoxPage(
          image: _imageFile!,
        ),
      ),
    );

    if (croppedFile != null) {
      setState(() {
        _croppedImageFile = croppedFile;
      });
    }
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Flutter Crop Box Example'),
      ),
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: <Widget>[
            _imageFile != null
                ? Image.file(_imageFile!)
                : Text('No image selected.'),
            SizedBox(height: 20),
            _croppedImageFile != null
                ? Image.file(_croppedImageFile!)
                : Text('No cropped image.'),
            SizedBox(height: 20),
            ElevatedButton(
              onPressed: _pickImage,
              child: Text('Pick Image'),
            ),
            SizedBox(height: 10),
            ElevatedButton(
              onPressed: _cropImage,
              child: Text('Crop Image'),
            ),
          ],
        ),
      ),
    );
  }
}

在这个示例中,我们做了以下几件事:

  1. 依赖添加:在pubspec.yaml中添加crop_boximage_picker依赖。
  2. 选择图片:使用image_picker插件从图库中选择图片。
  3. 裁剪图片:使用crop_box插件进行图片裁剪。
  4. 显示图片:在UI中显示选择的图片和裁剪后的图片。

注意:CropBoxPagecrop_box插件提供的一个页面,用于裁剪图片。用户选择裁剪区域后,点击确认按钮会返回裁剪后的图片文件。

这个示例展示了如何在Flutter应用中集成和使用crop_box插件进行图片裁剪。你可以根据需求进一步自定义和扩展这个示例。

回到顶部