Flutter Camera插件使用入门

0. 前言

开发时需要用到Camera 来进行视频图片截取, 因此来写一些这方面内容

1. 安装

pubspec.yaml 文件中添加 camera 依赖, 这里推荐使用一个vscode 插件:

  • Pubspec Assist: 可以很方便的管理dart 的包依赖

在这里插入图片描述

dependencies:
  flutter:
    sdk: flutter
  camera: ^0.5.7+4

1.1 iOS

找到目录 ios/Runner/Info.plis, 添加

<key>NSCameraUsageDescription</key>
<string>Can I use the camera please?</string>
<key>NSMicrophoneUsageDescription</key>
<string>Can I use the mic please?</string>

1.2 Android

将Android sdk 的最低版本 调到21 (或更高)

进入android/app/build.gradle 文件, 修改目标行为以下内容.

minSdkVersion 21

注意这里是android 的sdk最小版本, 与emulator最小版本不同, 所以确保自己的android emulator版本在27以上!

在这里插入图片描述

2. 测试项目

注意如果你使用官方的示例代码, 必须添加下面main()函数中的第一行,否则报错

2.1 示例代码

下面是完整正确的示例代码

File: d:\study\Android\Flutter\cameraTest\cameratest\lib\main.dart
1: import 'dart:async';
2: import 'package:flutter/material.dart';
3: import 'package:camera/camera.dart';
4: 
5: List<CameraDescription> cameras;
6: 
7: Future<void> main() async {
8:   WidgetsFlutterBinding.ensureInitialized();
9:   cameras = await availableCameras();
10:   runApp(CameraApp());
11: }
12: 
13: class CameraApp extends StatefulWidget {
14:   @override
15:   _CameraAppState createState() => _CameraAppState();
16: }
17: 
18: class _CameraAppState extends State<CameraApp> {
19:   CameraController controller;
20: 
21:   @override
22:   void initState() {
23:     super.initState();
24:     controller = CameraController(cameras[0], ResolutionPreset.medium);
25:     controller.initialize().then((_) {
26:       if (!mounted) {
27:         return;
28:       }
29:       setState(() {});
30:     });
31:   }
32: 
33:   @override
34:   void dispose() {
35:     controller?.dispose();
36:     super.dispose();
37:   }
38: 
39:   @override
40:   Widget build(BuildContext context) {
41:     if (!controller.value.isInitialized) {
42:       return Container();
43:     }
44:     return AspectRatio(
45:         aspectRatio:
46:         controller.value.aspectRatio,
47:         child: CameraPreview(controller));
48:   }
49: }

2.2 演示结果

依赖与代码都搞定之后就可以来打开测试了
按住alt+WASD 移动
演示详情

3. 代码讲解

下面对上面示例的某些代码进行逐行的详细的讲解

3.1 cameras描述

下面这行代码表示了所有的camera , 为什么是个List呢?
想一想, 我们的手机有多少个camera?
前置的, 后置的, 等等, 我们一个手机可以有好多camera , 因此他是一个List

5: List<CameraDescription> cameras;

注意这个虽然是用来描述cameras 的, 但是并不是我们手机相机真正的实例化对象, 我们不能用它来操作相机

3.2 camera controller

controller是真正的相机实例化对象, 我们可以用它来进行录制, 拍照等等
下面的代码中, cameras[0]一般代表手机后置摄像头, 用来拍景色用, 你可以把他改成cameras[1]这样子就是前置的了(你可以自己修改代码尝试一下)

  • initState()中进行相机初始化
    • 如果初始化失败了 就为未挂载状态(即 !mouted = true) ,那么就返回null值, 并且controller.value.isInitialized 变为false
    • 如果初始化成功, 那么controller.value.isInitialized变为true, 并且渲染CameraApp Widget
21:   @override
22:   void initState() {
23:     super.initState();
24:     controller = CameraController(cameras[0], ResolutionPreset.medium);
25:     controller.initialize().then((_) {
26:       if (!mounted) {
27:         return;
28:       }
29:       setState(() {});
30:     });
31:   }

3.3 dispose销毁对象

下面代码用来销毁controller

34:   void dispose() {
35:     controller?.dispose();
36:     super.dispose();
37:   }

为什么要进行销毁?

为了避免出现内存泄漏, controller是类内部的实例化对象, 所以显示的进行销毁, 避免出现内存泄漏

3.4 build 方法

39:   @override
40:   Widget build(BuildContext context) {
41:     if (!controller.value.isInitialized) {
42:       return Container();
43:     }
44:     return AspectRatio(
45:         aspectRatio:
46:         controller.value.aspectRatio,
47:         child: CameraPreview(controller));
48:   }

上面的代码中和上面所讲的相关

  • 如果初始化失败了 controller.value.isInitialized 为false, 就返回一个空白的Container(), 在用户看来就是空白的什么也没有
  • 如果初始化成功那么controller.value.isInitialized为true, 并且返回AspectRatio对象

3.3 CameraPreview 对象

虽然CameraPreview 对象 被一个AspectRadio对象包裹, 但是注意

  • AspectRatio 的英文意思是 宽高比 , 所以其实它是一个布局对象(与Camera 依赖包无关), 因此它会控制CemeraPreview对象的宽高比
  • CemeraPreview对象才是真正的摄像头界面对象, 需要一个摄像头实例化对象(这里是controller 作为参数) ,因此CameraPreview(controller)建立一个摄像头界面显示在界面中
  • 15
    点赞
  • 35
    收藏
    觉得还不错? 一键收藏
  • 6
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值