Sopheadavid Sopheap
Sopheadavid Sopheap

Reputation: 2874

Flutter: Unhandled Exception: ServicesBinding.defaultBinaryMessenger was accessed before the binding was initialized

Any solution to solve this problem?

Stacktrace:

[VERBOSE-2:ui_dart_state.cc(148)] Unhandled Exception: ServicesBinding.defaultBinaryMessenger was accessed before the binding was initialized.
If you're running an application and need to access the binary messenger before `runApp()` has been called (for example, during plugin initialization), then you need to explicitly call the `WidgetsFlutterBinding.ensureInitialized()` first.
If you're running a test, you can call the `TestWidgetsFlutterBinding.ensureInitialized()` as the first line in your test's `main()` method to initialize the binding.
#0      defaultBinaryMessenger.<anonymous closure> (package:flutter/src/services/binary_messenger.dart:73:7)
#1      defaultBinaryMessenger (package:flutter/src/services/binary_messenger.dart:86:4)
#2      MethodChannel.binaryMessenger (package:flutter/src/services/platform_channel.dart:140:62)
#3      MethodChannel.invokeMethod (package:flutter/src/services/platform_channel.dart:314:35)
<asynchronous suspension>
#4      MethodChannel.invokeMapMethod (package:f<…>

Upvotes: 285

Views: 137180

Answers (16)

sahil agrawal
sahil agrawal

Reputation: 17

Had the same problem... by adding

WidgetsFlutterBinding.ensureInitialized();

in void main() fixed my problem

void main() async {
  WidgetsFlutterBinding.ensureInitialized();
  await Firebase.initializeApp(
    options: DefaultFirebaseOptions.currentPlatform,
  );
  runApp(const MyApp());
}

`

Upvotes: 1

Adeel Nazim
Adeel Nazim

Reputation: 724

I had the same error by adding WidgetsFlutterBinding.ensureInitialized(); in the main resolved my problem.

Upvotes: 0

Sanjay Bharwani
Sanjay Bharwani

Reputation: 4749

Faced this problem while working on a udemy project xylophone_flutter

My flutter version is 3.16.9

flutter --version
Flutter 3.16.9 • channel stable • https://github.com/flutter/flutter.git

And my dart version is 3.2.6

  dart --version
Dart SDK version: 3.2.6 (stable) (Wed Jan 24 13:41:58 2024 +0000) on "macos_x64"

The issue was happening with the code to use audioplayers

Fix is to use WidgetsFlutterBinding.ensureInitialized(); before you initiate your App which attempts to use the AudioPlayer integration.

Below is the full working code.

import 'package:audioplayers/audioplayers.dart';
import 'package:flutter/material.dart';

void main() {
  WidgetsFlutterBinding.ensureInitialized();
  runApp(XylophoneApp());
}

class XylophoneApp extends StatelessWidget {
  final player = AudioPlayer();

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(title: Text('Xylophone')),
        body: SafeArea(
            child: Center(
          child: TextButton(
            onPressed: () {
              player.play(AssetSource('note2.wav'));
            },
            child: Text("Play"),
          ),
        )),
      ),
    );
  }
}

Upvotes: 1

ubershmekel
ubershmekel

Reputation: 12798

One possible solution is to close the flutter app, and start it up again.

I got this error when I flutter pub add shared_preferences then my web browser was trying to hot reload and failed. Stopping the debugging session and starting a new one made everything just work.

Upvotes: 0

Wasib Hussain
Wasib Hussain

Reputation: 256

By adding this line inside void main(), the error will be resolved.

WidgetsFlutterBinding.ensureInitialized();

Upvotes: 10

Jitesh Mohite
Jitesh Mohite

Reputation: 34180

This can be solved using WidgetsBinding.ensureInitialized() which established communication between the Dart Layer and Platform.

We need to call this method if we need the binding to be initialized before calling [runApp]. Flutter cannot directly interact with the flutter engine until and unless binding is established.

void main() async {
  WidgetsFlutterBinding.ensureInitialized();   
  /// Your Code which required binding
  runApp(
    ...
  )
}

WidgetsFlutterBinding.ensureInitialized() supports various binding such as

  1. ServicesBinding listens for platform messages and directs them to the handler for incoming messages (BinaryMessenger).

  2. PaintingBinding is responsible for binding to the painting library.

  3. RenderBinding binds the render tree to the Flutter engine.

  4. WidgetBinding binds the widget tree to the Flutter engine.

  5. SchedulerBinding is the scheduler for running immediate tasks.

  6. SemanticsBinding binds the semantics layer and the Flutter engine.

  7. GestureBinding is a binding for the gesture subsystem.

These all binding will act as a glue between Dart and Platform.

Upvotes: 7

ykonda
ykonda

Reputation: 527

It's worth nothing that if you are receiving this error from an isolate, then the accepted solution doesn't work.

WidgetsFlutterBinding.ensureInitialized();

only ensures the binding on the main thread.
There is work being done to be able to remove the restriction, you can follow that issue here

https://github.com/flutter/flutter/issues/13937

Upvotes: 4

sjsam
sjsam

Reputation: 21965

You could run into this if you're trying to execute plugin native code in an isolate. The isolate_handler documentation here explains this well:

Plugins use a mechanism called platform channel to communicate between the Dart and the native sides, a message passing mechanism using the MethodChannel type. This mechanism depends on elements of the underlying UI engine to function.

The catch here is that isolates will provide a performance boost only in the case of computationally expensive dart code. The plugin's platform code will again use the main(UI) thread again.

Calling WidgetsFlutterBinding.ensureInitialized inside an isolate will also fail because of the absence of an underlying UI engine in the isolate.

Upvotes: 14

Jesus Iniesta
Jesus Iniesta

Reputation: 12479

Solution: Call WidgetsFlutterBinding.ensureInitialized(); before calling asynchronous functions.


void main() async {
  WidgetsFlutterBinding.ensureInitialized();   //  ADD THIS BEFORE YOUR ASYNC FUNCTION CALL.
  await Firestore.instance.settings(...);      //  NOW YOU CAN CALL ASYNC FUNCTION.   
  ...
  runApp(
    ...
  )

Upvotes: 7

Achintha Isuru
Achintha Isuru

Reputation: 3307

An answer posted on the GitHub issue 47033 solved my problem.

issue: https://github.com/flutter/flutter/issues/47033

the solution that worked for me: https://github.com/flutter/flutter/issues/47033#issuecomment-571936089

I think this is an issue regarding the flutter version 1.12.13+hotfix maybe downgrading the flutter may help as well.

Upvotes: 0

hanslissi
hanslissi

Reputation: 235

Before I had the version v1.12.13+hotfix.5, then I switched to version v1.14.4 and it worked.

The error says that you should add WidgetsFlutterBinding.ensureInitialized();, but since that didn't work for me I switched to the other version. One thing to keep in mind though is that you still have to add WidgetsFlutterBinding.ensureInitialized(); as the very first line in your main!

Upvotes: 1

Debasmita Sarkar
Debasmita Sarkar

Reputation: 6589

This problem is introduced when you upgrade Flutter. The reason behind this is you are waiting for some data or running an async function inside main().

I was initialising ScopedModel inside main() and inside that I was awaiting for some data.

There is a very small fix. Just run WidgetsFlutterBinding.ensureInitialized() inside void main() , before you do runApp(). Works like a charm!!

void main() {
  WidgetsFlutterBinding.ensureInitialized();
  runApp(Delta(
    model: ProductDataModel(),
  ));
}

Upvotes: 607

arjava
arjava

Reputation: 1899

in my case when using orientation,

before solved :

void main() {
SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp]).then((_).{
runApp(MyApp());
});
}

solved use :

void main() {
WidgetsFlutterBinding.ensureInitialized();
SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp])
  .then((_) {
runApp(MyApp());
});
}

The point is to add WidgetsFlutterBinding.ensureInitialized() in the first line of the main class

Upvotes: 7

Saad Ahmed
Saad Ahmed

Reputation: 777

just add this line in main.dart

WidgetsFlutterBinding.ensureInitialized(); 

your code seems like

void main() {
  WidgetsFlutterBinding.ensureInitialized();
  return runApp(MultiProvider(
    providers: [
      ChangeNotifierProvider.value(
        value: AppState(),
      )
    ],
    child: MyApp(),
  ));
}

Upvotes: 18

CopsOnRoad
CopsOnRoad

Reputation: 267474

This generally happens if you are awaiting on main() method. So, the solution would be:

void main() {
  // add this, and it should be the first line in main method
  WidgetsFlutterBinding.ensureInitialized(); 

  // rest of your app code
  runApp(
    MaterialApp(...),
  );
}

Upvotes: 108

Mars
Mars

Reputation: 489

Not sure if I have the correct answer, but I got the same error after a recent flutter upgrade, and managed to get it to work, so I'm sharing my findings.

Looks like the error might be caused by a recent breaking change: https://groups.google.com/forum/#!msg/flutter-announce/sHAL2fBtJ1Y/mGjrKH3dEwAJ.

As a result, we need to manually change the code as follows:

  • If you're running an application and need to access the binary messenger before runApp() has been called (for example, during plugin initialization), then you need to explicitly call the WidgetsFlutterBinding.ensureInitialized() first.
  • If you're running a test, you can call the TestWidgetsFlutterBinding.ensureInitialized() as the first line in your test's main() method to initialize the binding.

Alternatively, if you are a newbie like me and struggling to understand the above and #38464, you can temporarily avoid this problem by switching to the beta channel. Just run "flutter channel beta". The breaking change is not in beta channel yet, so after switching to beta channel you wouldn't get this error at least for now.

Upvotes: 38

Related Questions