Flutter图像处理插件opencv_dart的使用
Flutter图像处理插件opencv_dart的使用
opencv_dart简介
opencv_dart
是用于Flutter的OpenCV库,它包含了所有的OpenCV模块。如果你不需要videoio
和highgui
模块,可以考虑使用opencv_core。
注意事项
从版本v1.3.0
开始,动态库将在本地构建,并在构建期间由Flutter调用。请注意:OpenCV SDK(约100M)将通过CMake的FetchContent
下载,你可以设置DARTCV_CACHE_DIR
环境变量来缓存它以避免重复下载。例如:export DARTCV_CACHE_DIR=$HOME/.cache/dartcv
- Q&A: #212 或者打开新问题。
- 如果你正在使用支持原生资源的Flutter特性,请考虑使用v2.x版本,详见native-assets分支,但此分支不会更新直到
Native Assets
稳定。
支持的平台
平台 | 是否支持 | 测试状态 | 架构 |
---|---|---|---|
Android | ✅ | ✅ | x86_64, arm64-v8a, armeabi-v7a |
iOS | ✅ | ✅ | arm64, x64(Simulator) |
Linux | ✅ | ✅ | x64, arm64 |
Windows | ✅ | ✅ | x64, arm64 |
macOS | ✅ | ✅ | x64, arm64 |
支持的模块
具体支持的模块列表请参阅这里
包大小
示例代码
下面是一个完整的示例demo,展示了如何使用opencv_dart
进行图像处理:
// ignore_for_file: avoid_print
import 'package:flutter/material.dart';
import 'package:image_picker/image_picker.dart';
import 'package:opencv_dart/opencv.dart' as cv;
void main() {
runApp(const MyApp());
}
class MyApp extends StatefulWidget {
const MyApp({super.key});
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
List<Uint8List> images = [];
Future<(cv.Mat, cv.Mat)> heavyTaskAsync(cv.Mat im, {int count = 1000}) async {
late cv.Mat gray, blur;
for (var i = 0; i < count; i++) {
gray = await cv.cvtColorAsync(im, cv.COLOR_BGR2GRAY);
blur = await cv.gaussianBlurAsync(im, (7, 7), 2, sigmaY: 2);
if (i != count - 1) {
gray.dispose(); // 手动释放
blur.dispose(); // 手动释放
}
}
return (gray, blur);
}
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('OpenCV Dart Example'),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
ElevatedButton(
onPressed: () async {
final picker = ImagePicker();
final img = await picker.pickImage(source: ImageSource.gallery);
if (img != null) {
final path = img.path;
final mat = cv.imread(path);
print("cv.imread: width: ${mat.cols}, height: ${mat.rows}, path: $path");
debugPrint("mat.data.length: ${mat.data.length}");
// 重计算任务
final (gray, blur) = await heavyTaskAsync(mat, count: 1);
setState(() {
images = [
cv.imencode(".png", mat).$2,
cv.imencode(".png", gray).$2,
cv.imencode(".png", blur).$2,
];
});
}
},
child: const Text("Pick Image"),
),
ElevatedButton(
onPressed: () async {
final data = await DefaultAssetBundle.of(context).load("images/lenna.png");
final bytes = data.buffer.asUint8List();
// 重计算任务
final (gray, blur) = await heavyTaskAsync(cv.imdecode(bytes, cv.IMREAD_COLOR));
setState(() {
images = [bytes, cv.imencode(".png", gray).$2, cv.imencode(".png", blur).$2];
});
},
child: const Text("Process"),
),
Expanded(
flex: 2,
child: Row(
children: [
Expanded(
child: ListView.builder(
itemCount: images.length,
itemBuilder: (ctx, idx) => Card(
child: Image.memory(images[idx]),
),
),
),
Expanded(
child: SingleChildScrollView(
child: Text(cv.getBuildInformation()),
),
),
],
),
),
],
),
),
),
);
}
}
说明
- heavyTaskAsync:该函数执行了颜色转换和高斯模糊操作,并返回灰度图和模糊后的图像。
- Pick Image按钮:允许用户从图库中选择图片,并对其进行颜色转换和高斯模糊处理,最后显示原始图像、灰度图像和模糊图像。
- Process按钮:加载内置的
lenna.png
图像并对其进行相同的处理。
更多示例可以参考官方示例或awesome-opencv_dart。
许可证
opencv_dart
遵循Apache-2.0 License。
希望这些信息对你有帮助!如果你有任何问题或需要进一步的帮助,请随时提问。
更多关于Flutter图像处理插件opencv_dart的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
更多关于Flutter图像处理插件opencv_dart的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
在Flutter中,使用opencv_dart
插件进行图像处理是一个强大的方法,因为OpenCV是一个广泛使用的计算机视觉库。虽然opencv_dart
主要是为Dart环境设计的,但你可以通过一些桥接技术在Flutter项目中使用它。下面是一个基本的示例,展示如何在Flutter中使用opencv_dart
进行图像处理。
首先,你需要在你的pubspec.yaml
文件中添加对opencv_dart
的依赖。然而,需要注意的是,opencv_dart
可能不是直接在Flutter插件库中可用的,因此你可能需要手动集成OpenCV的Dart绑定或者使用其他Flutter兼容的OpenCV封装。这里假设你已经有了相应的绑定或封装。
dependencies:
flutter:
sdk: flutter
opencv_dart: ^版本号 # 请注意,这里的版本号需要替换为实际可用的版本号
由于opencv_dart
可能不是官方支持的Flutter插件,接下来的步骤可能涉及一些原生代码集成或者使用现有的Flutter兼容库(如flutter_opencv
,如果存在的话)。以下是一个假设性的示例,展示如何在Flutter中调用OpenCV的功能。
假设性示例:在Flutter中使用OpenCV进行灰度转换
-
确保OpenCV Dart绑定已正确集成:
这一步可能涉及下载OpenCV的Dart绑定库,并将其包含在你的Flutter项目中。由于这不是一个标准的Flutter插件,你可能需要手动处理一些原生代码和构建配置。
-
创建一个Dart文件来处理OpenCV操作:
import 'package:opencv_dart/opencv_dart.dart'; class ImageProcessor { Mat convertToGrayscale(Uint8List imageBytes, int width, int height) { // 创建一个Mat对象从图像字节数据 Mat src = Mat.fromBytes(width, height, Mat.CV_8UC4, imageBytes); // 转换到灰度图像 Mat dst = Mat(); cv.cvtColor(src, dst, cv.COLOR_BGR2GRAY); return dst; } }
-
在Flutter Widget中使用这个处理器:
import 'package:flutter/material.dart'; import 'dart:typed_data'; import 'image_processor.dart'; // 假设你的ImageProcessor类在这里 void main() { runApp(MyApp()); } class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp( home: Scaffold( appBar: AppBar( title: Text('OpenCV in Flutter'), ), body: Center( child: ImageFromOpenCV(), ), ), ); } } class ImageFromOpenCV extends StatefulWidget { @override _ImageFromOpenCVState createState() => _ImageFromOpenCVState(); } class _ImageFromOpenCVState extends State<ImageFromOpenCV> { Uint8List? grayscaleImageBytes; @override void initState() { super.initState(); loadAndProcessImage(); } void loadAndProcessImage() async { // 这里你应该加载你的图像数据,例如从资产文件夹或网络 // 这里为了简化,我们假设已经有了一个图像字节数组 Uint8List imageBytes = ...; // 你的图像字节数据 int width = ...; // 图像宽度 int height = ...; // 图像高度 ImageProcessor processor = ImageProcessor(); Mat grayscaleMat = processor.convertToGrayscale(imageBytes, width, height); // 将Mat对象转换回字节数据(这里需要一些额外的处理,因为Mat对象不是直接可序列化的) // 注意:这里的转换代码可能需要根据你使用的OpenCV Dart绑定的具体实现来调整 Uint8ListBuffer buffer = Uint8ListBuffer(); grayscaleMat.writeTo(buffer); grayscaleImageBytes = buffer.asUint8List(); // 更新UI setState(() {}); } @override Widget build(BuildContext context) { return grayscaleImageBytes != null ? Image.memory(grayscaleImageBytes!) : CircularProgressIndicator(); } }
注意:上面的代码示例包含了一些假设和简化的部分,特别是关于如何加载图像数据和如何将Mat
对象转换回字节数据的部分。在实际应用中,你可能需要使用更复杂的逻辑来处理这些任务,特别是如果你正在处理从相机或网络加载的图像。
此外,由于opencv_dart
可能不是直接在Flutter生态系统中广泛使用的库,因此你可能需要查找或创建与Flutter兼容的OpenCV绑定。如果这样的绑定不存在,你可能需要考虑使用平台通道(Platform Channels)来在Flutter和原生代码之间通信,从而在原生侧使用OpenCV。