ekasetiawans / flutter_background_service

265 stars 183 forks source link

Unable to call method channel from my background service. #299

Open dilipkaklotar opened 1 year ago

dilipkaklotar commented 1 year ago

Below code are my android MainActivity.kt


    private val PRINTER_CHNNEL = "TabLessPrinter"

    private lateinit var channel: MethodChannel

    override fun configureFlutterEngine(flutterEngine: FlutterEngine) {

        super.configureFlutterEngine(flutterEngine)

        channel = MethodChannel(flutterEngine.dartExecutor.binaryMessenger, PRINTER_CHNNEL)

        //Receive

        channel.setMethodCallHandler{ call , result ->

           if(call.method == "OnlyLog") {

               Log.d("OnlyLog", "---------------------------------------->>>>");
               Log.d("OnlyLog", "---------------Demo Message-----------------");
               Log.d("OnlyLog", "---------------------------------------->>>>");

           }

        }

    }

BACKGROUND SERVICE CODE AS MENTIONED BELOW

 Future<void> initializeService() async {
  final service = FlutterBackgroundService();

  const AndroidNotificationChannel channel = AndroidNotificationChannel(
    'my_foreground', // id
    'GO TABLESS FOREGROUND SERVICE', // title
    description:
    'This channel is used for important notifications.', // description
    importance: Importance.low, // importance must be at low or higher level
  );

  final FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
  FlutterLocalNotificationsPlugin();

  if (Platform.isIOS) {
    await flutterLocalNotificationsPlugin.initialize(
      const InitializationSettings(
        iOS: DarwinInitializationSettings(),
      ),
    );
  }

  await flutterLocalNotificationsPlugin
      .resolvePlatformSpecificImplementation<
      AndroidFlutterLocalNotificationsPlugin>()
      ?.createNotificationChannel(channel);

  await service.configure(
    androidConfiguration: AndroidConfiguration(
      onStart: onStart,
      autoStart: true,
      isForegroundMode: true,// false
      autoStartOnBoot: true,
      notificationChannelId: 'my_foreground',
      initialNotificationTitle: 'TABLESS SERVICE',
      initialNotificationContent: 'Initializing',
      foregroundServiceNotificationId: 888,
    ),
    iosConfiguration: IosConfiguration(
      autoStart: true,
      onForeground: onStart,
      onBackground: onIosBackground,
    ),
  );
  service.startService();
}

@pragma('vm:entry-point')
Future<bool> onIosBackground(ServiceInstance service) async {
  WidgetsFlutterBinding.ensureInitialized();
  DartPluginRegistrant.ensureInitialized();

  return true;
}

@pragma('vm:entry-point')
void onStart(ServiceInstance service) async {
  DartPluginRegistrant.ensureInitialized();

  final FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
  FlutterLocalNotificationsPlugin();

  if (service is AndroidServiceInstance) {
    service.on('setAsForeground').listen((event) {
      service.setAsForegroundService();
    });

    service.on('setAsBackground').listen((event) {
      service.setAsBackgroundService();
    });
  }

  if(service is IOSServiceInstance){
    service.on('setAsForeground').listen((event) {
      service.invoke('setAsForeground');
    });

    service.on('setAsBackground').listen((event) {
      service.invoke('setAsBackground');
    });
  }

  service.on('stopService').listen((event) {
    service.stopSelf();
  });

  Timer.periodic(const Duration(seconds: 5), (timer) async {
    if (service is AndroidServiceInstance) {
      if (await service.isForegroundService()) {
        print('FLUTTER FOREGROUND SERVICE: ${DateTime.now()}');
        try {

          PrintTest.printMessage();
        } catch (e) {

        }
      }
    }
  });

}
 import 'package:flutter/cupertino.dart';
import 'package:flutter/services.dart';

class PrintTest {

  static Future<void> printMessage() async {
    try {
      WidgetsFlutterBinding.ensureInitialized();
      var _channel = const MethodChannel('TabLessPrinter');
      await _channel.invokeMethod('OnlyLog');
    } on PlatformException catch (e) {
      print("Failed to invoke method: ${e.message}");
    }
  }

}

Kindly guide me why its not working.

arpitsharma007 commented 1 year ago

When app is killed the main activity gets destroyed and therefore your method channel code in kotlin also gets removed. This is the reason why your method channel is not being called.

dilipkaklotar commented 1 year ago

@arpitsharma007 So what is the solution for that. and also application is in foreground then also I am not able to call method channel.

ranjitIN commented 1 year ago

i am also trying to call method channel but its not working. can anyone help me on this.

Leylan24 commented 1 year ago

@ranjitIN @dilipkaklotar have you guys found a solution to this yet?

ranjitIN commented 1 year ago

@Leylan24 yup if you want to call method channel in flutter in background service create a flutter package for all of your method channel and use the package on your dependency. Developing packages and plugins

Leylan24 commented 1 year ago

@ranjitIN so wrap the plugins inside a package? Also if i used dart:ui package inside any of the plugins then would it still work ?

Gonn01 commented 4 days ago

@Leylan24 yup if you want to call method channel in flutter in background service create a flutter package for all of your method channel and use the package on your dependency. Developing packages and plugins

Hello, i created a flutter package and added it as a dependency to my project, also added the method im trying to call inside the MainActivity.kt of the new flutter package,(i test it by running it and work) but when im trying to call the method on my project throws Unhandled Exception: MissingPluginException(No implementation found for method getLocation on channel location_channel), someone knows whats happening?

ekasetiawans commented 4 days ago

any method channel thats requires native Activity class will not works with this plugin