Navaron Bracke

handle errors with onDetect

@@ -21,6 +21,7 @@ class MobileScanner extends StatefulWidget { @@ -21,6 +21,7 @@ class MobileScanner extends StatefulWidget {
21 const MobileScanner({ 21 const MobileScanner({
22 this.controller, 22 this.controller,
23 this.onDetect, 23 this.onDetect,
  24 + this.onDetectError = _onDetectErrorHandler,
24 this.fit = BoxFit.cover, 25 this.fit = BoxFit.cover,
25 this.errorBuilder, 26 this.errorBuilder,
26 this.overlayBuilder, 27 this.overlayBuilder,
@@ -34,15 +35,17 @@ class MobileScanner extends StatefulWidget { @@ -34,15 +35,17 @@ class MobileScanner extends StatefulWidget {
34 final MobileScannerController? controller; 35 final MobileScannerController? controller;
35 36
36 /// The function that signals when new codes were detected by the [controller]. 37 /// The function that signals when new codes were detected by the [controller].
37 - /// If null, use the controller.barcodes stream directly to capture barcodes.  
38 - ///  
39 - /// This method does not receive any [MobileScannerBarcodeException]s  
40 - /// that are emitted by the scanner.  
41 /// 38 ///
42 /// To handle both [BarcodeCapture]s and [MobileScannerBarcodeException]s, 39 /// To handle both [BarcodeCapture]s and [MobileScannerBarcodeException]s,
43 - /// use the [MobileScannerController.barcodes] stream directly. 40 + /// use the [MobileScannerController.barcodes] stream directly (recommended),
  41 + /// or provide a function to [onDetectError].
44 final void Function(BarcodeCapture barcodes)? onDetect; 42 final void Function(BarcodeCapture barcodes)? onDetect;
45 43
  44 + /// The error handler equivalent for the [onDetect] function.
  45 + ///
  46 + /// If [onDetect] is not null, and this is null, errors are silently ignored.
  47 + final void Function(Object error, StackTrace stackTrace) onDetectError;
  48 +
46 /// The error builder for the camera preview. 49 /// The error builder for the camera preview.
47 /// 50 ///
48 /// If this is null, a black [ColoredBox], 51 /// If this is null, a black [ColoredBox],
@@ -122,6 +125,11 @@ class MobileScanner extends StatefulWidget { @@ -122,6 +125,11 @@ class MobileScanner extends StatefulWidget {
122 125
123 @override 126 @override
124 State<MobileScanner> createState() => _MobileScannerState(); 127 State<MobileScanner> createState() => _MobileScannerState();
  128 +
  129 + /// This empty function is used as the default error handler for [onDetect].
  130 + static void _onDetectErrorHandler(Object error, StackTrace stackTrace) {
  131 + // Do nothing.
  132 + }
125 } 133 }
126 134
127 class _MobileScannerState extends State<MobileScanner> 135 class _MobileScannerState extends State<MobileScanner>
@@ -255,7 +263,11 @@ class _MobileScannerState extends State<MobileScanner> @@ -255,7 +263,11 @@ class _MobileScannerState extends State<MobileScanner>
255 void initState() { 263 void initState() {
256 if (widget.onDetect != null) { 264 if (widget.onDetect != null) {
257 WidgetsBinding.instance.addObserver(this); 265 WidgetsBinding.instance.addObserver(this);
258 - _subscription = controller.barcodes.listen(widget.onDetect); 266 + _subscription = controller.barcodes.listen(
  267 + widget.onDetect,
  268 + onError: widget.onDetectError,
  269 + cancelOnError: false,
  270 + );
259 } 271 }
260 if (controller.autoStart) { 272 if (controller.autoStart) {
261 controller.start(); 273 controller.start();
@@ -297,7 +309,11 @@ class _MobileScannerState extends State<MobileScanner> @@ -297,7 +309,11 @@ class _MobileScannerState extends State<MobileScanner>
297 case AppLifecycleState.paused: 309 case AppLifecycleState.paused:
298 return; 310 return;
299 case AppLifecycleState.resumed: 311 case AppLifecycleState.resumed:
300 - _subscription = controller.barcodes.listen(widget.onDetect); 312 + _subscription = controller.barcodes.listen(
  313 + widget.onDetect,
  314 + onError: widget.onDetectError,
  315 + cancelOnError: false,
  316 + );
301 317
302 unawaited(controller.start()); 318 unawaited(controller.start());
303 case AppLifecycleState.inactive: 319 case AppLifecycleState.inactive: