简体   繁体   English

Flutter WorkManager 后台获取示例与 StateFull 小部件

[英]Flutter WorkManager Background Fetch Example With StateFull Widget

I have a function called control in the StateFull Widget.我在 StateFull Widget 中有一个名为 control 的 function。 I want to run this function with WorkManager every 15 minutes.我想每 15 分钟用 WorkManager 运行这个 function。

How can I call the control function from the callbackDispatcher function?如何从 callbackDispatcher function 调用控件 function? I added a Stream statically to the Statefull widget and then listened to it but it didn't work.我将 Stream 静态添加到 Statefull 小部件,然后听了它,但它没有用。

HomeScreen.dart file HomeScreen.dart 文件

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

const taskKontrol = "control";

class HomeScreen extends StatefulWidget {
  @override
  _HomeScreenState createState() => _HomeScreenState();
}

class _HomeScreenState extends State<HomeScreen> {
  @override
  Widget build(BuildContext context) {
    return Container();
  }

  @override
  void initState() {
    super.initState();
    setupWorkManager();
  }

  void control() async
  {
    //... my code control is here
  }

}

void setupWorkManager() async {
  await Workmanager.initialize(callbackDispatcher, isInDebugMode: true);
  Workmanager.registerPeriodicTask(taskKontrol, taskKontrol,
      frequency: Duration(seconds: 10),
      existingWorkPolicy: ExistingWorkPolicy.append
  );
}


void callbackDispatcher() {
  Workmanager.executeTask((taskName, inputData) async {
    switch(taskName)
    {
      case taskKontrol:
        // How can I call the control function from here?
        print("control from workmanager");
        break;
    }
    return Future.value(true);
  });
}

For those who still looking for an answer:对于那些仍在寻找答案的人:

From the official docs:来自官方文档:

The callbackDispatcher needs to be either a static function or a top level function to be accessible as a Flutter entry point. The callbackDispatcher needs to be either a static function or a top level function to be accessible as a Flutter entry point.

I had this same problem and I solved it by moving the function callbackDispatcher to the file: main.dart我遇到了同样的问题,我通过将 function callbackDispatcher移动到文件来解决它: main.dart

Also, the code that initializes callbackDispatcher must be in main() before the App() widget loads.此外,初始化callbackDispatcher的代码必须在App()小部件加载之前位于main()中。

To call your control code, create a class with static function control()要调用您的控制代码,请使用 static function control()

Note: You cannot call the widget's method from callbackDispatcher!注意:您不能从 callbackDispatcher 调用小部件的方法!

Reason: Widgets are UI bound.原因:小部件是 UI 绑定的。 As long as the screen remains active, the widget that is visible remains active.只要屏幕保持活动状态,可见的小部件就会保持活动状态。 Once you close the app or move on to next screen, the widgets' memory gets recycled.关闭应用程序或移至下一个屏幕后,小部件的 memory 将被回收。 But this callbackDispatcher gets executed even when your app is closed.但是即使你的应用程序关闭,这个 callbackDispatcher 也会被执行。 So, it has to be isolated from UI code.因此,它必须与 UI 代码隔离。

Here's the code:这是代码:

main.dart: main.dart:

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


void main() async {
  WidgetsFlutterBinding.ensureInitialized();
  await Workmanager().initialize(callbackDispatcher, isInDebugMode: true);
  runApp(App());
}

void callbackDispatcher() {
  Workmanager.executeTask((taskName, inputData) async {
    switch(taskName)
    {
      case ScheduledTask.taskName:
        ScheduledTask.control(); // calls your control code
        break;
    }
    return Future.value(true);
  });
}

class ScheduledTask {
  const static String taskName = "control";
  static void control() {
    // add your control here
  }
}

All you can do from HomeScreen widget is to call setupWorkManager() that schedules the task您可以从 HomeScreen 小部件中做的所有事情就是调用setupWorkManager()来安排任务

class _HomeScreenState extends State<HomeScreen> {
  @override
  Widget build(BuildContext context) {
    return Container();
  }

  @override
  void initState() {
    super.initState();
    setupWorkManager();
  }
}

void setupWorkManager() async {
  Workmanager.registerPeriodicTask(taskKontrol, taskKontrol,
      frequency: Duration(minutes: 15),
      existingWorkPolicy: ExistingWorkPolicy.append
  );
}

Note: The minimum frequency for the recurring task is 15 minutes注意:重复任务的最低频率为 15 分钟

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM