我一直在尝试制作一个 flutter 应用程序来检测对象并在它们周围放置边界框。首先,当我收到相机反馈时,它工作正常,但当我加载模型并尝试运行它时,它就无法工作,并且会在 2 3 秒内崩溃。
我已经尝试了从优化模型到更改模型本身的所有方法,但似乎没有任何效果,任何帮助将不胜感激。我附上完整的代码:
import 'dart:async';
import 'dart:math' as math;
import 'dart:typed_data';
import 'dart:ui' as ui;
import 'package:camera/camera.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:tflite/tflite.dart';
import 'package:flutter/rendering.dart';
late List<CameraDescription> _cameras;
Future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
_cameras = await availableCameras();
await loadModel();
runApp(const MyApp());
}
Future<void> loadModel() async {
String? res = await Tflite.loadModel(
model: "assets/ssdmobilenet.tflite",
labels: "assets/label2.txt",
numThreads: 4, // defaults to 1
isAsset:
true, // defaults to true, set to false to load resources outside assets
useGpuDelegate:
false // defaults to false, set to true to use GPU delegate
);
print('model loaded successfully');
}
Future<List<dynamic>?> runModelOnFrame(CameraImage image) async {
var recognitions = await Tflite.detectObjectOnFrame(
bytesList: image.planes.map((plane) {
return plane.bytes;
}).toList(),
model: "YOLO",
imageHeight: image.height,
imageWidth: image.width,
imageMean: 0, // defaults to 127.5
imageStd: 255, // defaults to 127.5
threshold: 0.2, // defaults to 0.1
numResultsPerClass: 1,
);
print('Found ${recognitions?.length ?? 0} objects');
return recognitions;
}
class MyApp extends StatefulWidget {
const MyApp({Key? key});
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
@override
Widget build(BuildContext context) {
return const MaterialApp(
debugShowCheckedModeBanner: false,
home: FIrstPage(),
);
}
}
class FIrstPage extends StatefulWidget {
const FIrstPage({Key? key});
@override
State<FIrstPage> createState() => _FIrstPageState();
}
class _FIrstPageState extends State<FIrstPage> {
String buttonName = 'HEYO';
int currentIndex = 0;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('App Bar'),
),
body: Center(
child: currentIndex == 0
? Container(
color: Colors.blue,
width: double.infinity,
height: double.infinity,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
ElevatedButton(
style: ElevatedButton.styleFrom(
primary: Colors.white,
onPrimary: Colors.black,
),
onPressed: () {
Navigator.of(context).push(
MaterialPageRoute(
builder: (BuildContext conext) =>
Scaffold(body: const CameraApp()),
),
);
},
child: Text(buttonName),
),
ElevatedButton(
onPressed: () {
Navigator.of(context).push(
MaterialPageRoute(
builder: (BuildContext context) => const NewPage(),
),
);
},
child: Text(buttonName),
),
],
),
)
: Image.asset('images/light.jpg'),
),
bottomNavigationBar: BottomNavigationBar(
items: const [
BottomNavigationBarItem(label: 'home', icon: Icon(Icons.home)),
BottomNavigationBarItem(label: 'settings', icon: Icon(Icons.settings))
],
currentIndex: currentIndex,
onTap: (int index) {
setState(() {
currentIndex = index;
});
},
),
);
}
}
class NewPage extends StatelessWidget {
const NewPage({Key? key});
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(),
);
}
}
class CameraApp extends StatefulWidget {
/// Default Constructor
const CameraApp({Key? key});
@override
State<CameraApp> createState() => _CameraAppState();
}
class _CameraAppState extends State<CameraApp> {
bool isProcessingFrame = false;
late CameraController controller;
List<Widget> boxesWidgets = [];
int processingFrames = 0;
@override
void initState() {
super.initState();
controller = CameraController(_cameras[0], ResolutionPreset.medium);
controller.initialize().then((_) {
if (!mounted) {
return;
}
setState(() {});
controller.startImageStream(_onImageAvailable);
});
}
Future<void> _onImageAvailable(CameraImage image) async {
processingFrames++;
if (isProcessingFrame) {
return;
}
isProcessingFrame = true;
processingFrames++;
if (processingFrames >= 3) {
processingFrames = 0;
}
List<dynamic>? recognitions = await runModelOnFrame(image);
if (recognitions != null) {
List<Widget> boxes = [];
for (var recognition in recognitions) {
double confidence = recognition['confidence'];
if (confidence >= 0.1) {
int index = recognition['index'];
String label = recognition['label'];
double left = recognition['rect']['x'];
double top = recognition['rect']['y'];
double width = recognition['rect']['w'];
double height = recognition['rect']['h'];
double right = left + width;
double bottom = top + height;
// Convert coordinates from relative [0, 1] range to absolute values.
left *= image.width;
top *= image.height;
width *= image.width;
height *= image.height;
right *= image.width;
bottom *= image.height;
boxes.add(
Positioned(
left: left,
top: top,
width: width,
height: height,
child: Container(
decoration: BoxDecoration(
border: Border.all(
color: Colors.green,
width: 2,
),
),
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Text(
'$label ${(confidence * 100).toStringAsFixed(0)}%',
style: const TextStyle(
color: Colors.green,
fontWeight: FontWeight.bold,
fontSize: 16,
),
),
],
),
),
),
);
}
}
setState(() {
boxesWidgets = boxes;
});
}
}
@override
Widget build(BuildContext context) {
if (!controller.value.isInitialized) {
return Container();
}
final size = MediaQuery.of(context).size;
final deviceRatio = size.width / size.height;
return Scaffold(
body: Stack(
children: <Widget>[
Center(
child: AspectRatio(
aspectRatio: deviceRatio,
child: CameraPreview(controller),
),
),
...boxesWidgets,
],
),
);
}
@override
void dispose() {
controller.stopImageStream();
controller.dispose();
super.dispose();
}
}
尝试添加???在你的第一行 label.txt
1.??? 2.class1 3.2级