gpt4 book ai didi

flutter - GetxControllers 是否会自动关闭 obs 流?

转载 作者:行者123 更新时间:2023-12-03 03:21:17 28 4
gpt4 key购买 nike

我正在使用以下包https://pub.dev/packages/get .我需要在 GetxController 的 onClose 中关闭我的 .obs 吗?我在文档中找不到任何关于此的内容。看着我的内存,似乎它们正在被自动销毁。

最佳答案

到目前为止,我对 GetX + Flutter 的理解...
不,您不必删除 close() 中的 .obs GetxControllers 的方法。当 Controller 从内存中删除时, Controller 中的可观察对象的处理会自动完成。
当包含它们的小部件从小部件堆栈中弹出/从小部件树中删除时,GetX 会处理/删除 GetxControllers(及其可观察对象) (默认情况下,但可以被覆盖)。
您可以在 dispose() 的覆盖中看到这一点各种 Get 小部件的方法。
这是 dispose() 的片段在 GetX 时运行小部件被弹出/删除:

  @override
void dispose() {
if (widget.dispose != null) widget.dispose(this);
if (isCreator || widget.assignId) {
if (widget.autoRemove && GetInstance().isRegistered<T>(tag: widget.tag)) {
GetInstance().delete<T>(tag: widget.tag);
}
}
subs.cancel();
_observer.close();
controller = null;
isCreator = null;
super.dispose();
}
当您使用绑定(bind)或 Get.to()您正在使用 GetPageRoute是通过路由名称进行清理的:
  @override
void dispose() {
if (Get.smartManagement != SmartManagement.onlyBuilder) {
WidgetsBinding.instance.addPostFrameCallback((_) => GetInstance()
.removeDependencyByRoute("${settings?.name ?? routeName}"));
}
super.dispose();
}
测试应用
下面是一个测试应用程序,您可以将其复制/粘贴到 Android Studio/VSCode 中并运行以查看调试或运行窗口输出以获得 GETX 生命周期事件。
GetX 将记录 Controller 在内存中的创建和处理。
GetX Output Log
该应用程序有一个 HomePage 和 3 个 ChildPages,它们以 3 种方式使用 Get Controller,所有这些都从内存中删除:
  • GetX/GetBuilder
  • 获取.put
  • 绑定(bind)
  • import 'package:flutter/material.dart';
    import 'package:get/get.dart';

    void main() {
    // MyCounterBinding().dependencies(); // usually where Bindings happen
    runApp(MyApp());
    }

    class MyApp extends StatelessWidget {
    @override
    Widget build(BuildContext context) {
    return GetMaterialApp(
    title: 'GetX Dispose Ex',
    home: HomePage(),
    );
    }
    }

    class HomePage extends StatelessWidget {
    @override
    Widget build(BuildContext context) {
    return Scaffold(
    appBar: AppBar(
    title: Text('GetX Dispose Test'),
    ),
    body: Center(
    child: Column(
    mainAxisAlignment: MainAxisAlignment.spaceEvenly,
    children: [
    RaisedButton(
    child: Text('GetX/Builder Child'),
    onPressed: () => Get.to(ChildPage()),
    ),
    RaisedButton(
    child: Text('Get.put Child'),
    onPressed: () => Get.to(ChildPutPage()),
    ),
    RaisedButton(
    child: Text('Binding Child'),
    onPressed: () => Get.to(ChildBindPage()),
    ),
    ],
    ),
    ),
    );
    }
    }

    /// GETX / GETBUILDER
    /// Creates Controller within the Get widgets
    class ChildPage extends StatelessWidget {
    @override
    Widget build(BuildContext context) {
    return Scaffold(
    appBar: AppBar(
    title: Text('GetX Dispose Test Counter'),
    ),
    body: Center(
    child: Column(
    mainAxisAlignment: MainAxisAlignment.spaceEvenly,
    children: [
    Text('This is the Child Page'),
    GetX<ChildX>(
    init: ChildX(),
    builder: (cx) => Text('Counter: ${cx.counter}', style: TextStyle(fontSize: 20),),
    ),
    GetBuilder<ChildX>(
    init: ChildX(),
    builder: (cx) => RaisedButton(
    child: Text('Increment'),
    onPressed: cx.inc,
    ),
    ),
    ],
    ),
    ),
    );
    }
    }

    /// GET.PUT
    /// Creates Controller instance upon Build, usable anywhere within the widget build context
    class ChildPutPage extends StatelessWidget {
    //final ChildX cx = Get.put(ChildX()); // wrong place to put
    // see https://github.com/jonataslaw/getx/issues/818#issuecomment-733652172

    @override
    Widget build(BuildContext context) {
    final ChildX cx = Get.put(ChildX());
    return Scaffold(
    appBar: AppBar(
    title: Text('GetX Dispose Test Counter'),
    ),
    body: Center(
    child: Column(
    mainAxisAlignment: MainAxisAlignment.spaceEvenly,
    children: [
    Text('This is the Child Page'),
    Obx(
    () => Text('Counter: ${cx.counter}', style: TextStyle(fontSize: 20),),
    ),
    RaisedButton(
    child: Text('Increment'),
    onPressed: cx.inc,
    )
    ],
    ),
    ),
    );
    }
    }

    class MyCounterBinding extends Bindings {
    @override
    void dependencies() {
    Get.lazyPut(() => ChildX(), fenix: true);
    }
    }

    /// GET BINDINGS
    /// Normally the MyCounterBinding().dependencies() call is done in main(),
    /// making it available throughout the entire app.
    /// A lazyPut Controller /w [fenix:true] will be created/removed/recreated as needed or
    /// as specified by SmartManagement settings.
    /// But to keep the Bindings from polluting the other examples, it's done within this
    /// widget's build context (you wouldn't normally do this.)
    class ChildBindPage extends StatelessWidget {
    @override
    Widget build(BuildContext context) {
    MyCounterBinding().dependencies(); // just for illustration/example

    return Scaffold(
    appBar: AppBar(
    title: Text('GetX Dispose Test Counter'),
    ),
    body: Center(
    child: Column(
    mainAxisAlignment: MainAxisAlignment.spaceEvenly,
    children: [
    Text('This is the Child Page'),
    Obx(
    () => Text('Counter: ${ChildX.i.counter}', style: TextStyle(fontSize: 20),),
    ),
    RaisedButton(
    child: Text('Increment'),
    onPressed: ChildX.i.inc,
    )
    ],
    ),
    ),
    );
    }
    }


    class ChildX extends GetxController {
    static ChildX get i => Get.find();
    RxInt counter = 0.obs;

    void inc() => counter.value++;
    }
    笔记
    Get.to 与 Navigator.push
    使用 Get.put() 时在子小部件中确保您使用的是 Get.to()导航到那个 child 而不是 Flutter 的内置 Navigator.push .
    GetX 将目标小部件包装在 GetPageRoute 中。使用 Get.to 时.当导航离开/将小部件从堆栈中弹出时,此 Route 类将处理此路由中的 Controller 。如果您使用 Navigator.push , GetX 不参与,你不会得到这个自动清理。
    Navigator.push
    onPressed: () => Navigator.push(context, MaterialPageRoute(
    builder: (context) => ChildPutPage())),
    前往
    onPressed: () => Get.to(ChildPutPage()),

    关于flutter - GetxControllers 是否会自动关闭 obs 流?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62990128/

    28 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com