如何Flutter Getx将Obs绑定到Widget? [英] how to Flutter Getx binds obs to Widget?

查看:418
本文介绍了如何Flutter Getx将Obs绑定到Widget?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

当我使用 Getx 更新我的窗口小部件时?我不知道 Rx()如何联系我放入的东西.

when I use Getx to update my Widget? I do not know Rx() how to contact to the thing I put in.

code是 _obx = Rx().但我发送的数据是.".obs .不是 Rx(),而是 RxString().当我使用" .. obs.value ="newString" 时.为什么 Rx()可以知道谁更新数据.

code is _obx=Rx(). but I send data is "".obs. that is not Rx() but this is RxString(). when I use "".obs.value="newString". why Rx() can know that who updates data.

就像:

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

class GetIncrementPage extends StatefulWidget {
  GetIncrementPage({Key key}) : super(key: key);

  @override
  _GetIncrementPageState createState() => _GetIncrementPageState();
}

class _GetIncrementPageState extends State<GetIncrementPage> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('get'),
      ),
      body: Container(
        alignment: Alignment.center,
        child: _body(),
      ),
    );
  }

  Widget _body() {
    return Column(
      mainAxisAlignment: MainAxisAlignment.center,
      crossAxisAlignment: CrossAxisAlignment.center,
      children: [
        OutlineButton(
          child: Text('get 数字加减'),
          onPressed: c.increment,
        ),
        OutlineButton(
          child: Text('get log 变化'),
          onPressed: c.change,
        ),

        Obx(() {
          printInfo(info: '刷新了页面 get_example');
          return Text(c.count.toString());
        }),

        ObxValue((v) {
          printInfo(info: '刷新了页面 get_ObxValue_log1 ');
          return Text('logValue:' + v.toString());
        }, ObjectKey('key').obs),

        Obx(() {
          printInfo(info: '刷新了页面 get_obx_log1');

          return Text('logObx:' + c.log.toString());
        }),
        Obx(() {
          printInfo(info: '刷新了页面 get_obx_log2');

          return Text(c.log2.toString());
        }),

        // ObxValue((var value) => Text('${value.toString()}'), c),
      ],
    );
  }

  @override
  void dispose() {
    Get.delete<Controller2>();
    super.dispose();
  }

  final Controller2 c = Get.put(Controller2());
}

///
/// Created by fgyong on 2020/10/22.
///

class Controller2 extends GetxController {
  var count = 0.obs;
  var count2 = 0.obs;

  final log = ''.obs;
  final log2 = ''.obs;

  increment() => count++;
  @override
  void onClose() {
    printInfo(info: 'Controller close');
    super.onClose();
  }

  void change() {
    log.value += ' ${log.value.length}';
  }
}

当我将log.value更改为新的String时,为什么log2不新鲜.

when i change log.value to new String,why log2 do not fresh.

class Obx extends StatefulWidget {
  final WidgetCallback builder;

  const Obx(this.builder);

  _ObxState createState() => _ObxState();
}

class _ObxState extends State<Obx> {
  RxInterface _observer;
  StreamSubscription subs;

  _ObxState() {
    _observer = Rx();
  }

  @override
  void initState() {
    subs = _observer.subject.stream.listen((data) => setState(() {}));
    super.initState();
  }

  @override
  void dispose() {
    subs.cancel();
    _observer.close();
    super.dispose();
  }

  Widget get notifyChilds {
    final observer = getObs;
    getObs = _observer;
    final result = widget.builder();
    if (!_observer.canUpdate) {
      throw """
      [Get] the improper use of a GetX has been detected. 
      You should only use GetX or Obx for the specific widget that will be updated.
      If you are seeing this error, you probably did not insert any observable variables into GetX/Obx 
      or insert them outside the scope that GetX considers suitable for an update 
      (example: GetX => HeavyWidget => variableObservable).
      If you need to update a parent widget and a child widget, wrap each one in an Obx/GetX.
      """;
    }
    getObs = observer;
    return result;
  }

  @override
  Widget build(BuildContext context) => notifyChilds;
}

为什么rx()可以与日志建立联系,请帮助我.当我更新Rx()如何在登录时知道?

Why can rx() establish contact with the log, please help me. When I update How can Rx() know when logging?

请帮帮我.

推荐答案

您可以在Get中使用 Obx GetX 小部件来收听";更改您在GetxController中声明的可观察变量.

You can use Obx or GetX widgets from Get to "listen" to changes to observable variables you declare in a GetxController.

我认为您也将Rx作为ObserVER与ObservABLE混淆了.Rx是可观察到的,即您可以使用Obx或GetX小部件来监视它的变化(我想您可以将这两个小部件称为观察者".)

I think you are also confusing Rx as an ObserVER vs. ObservABLE. Rx is an observable, i.e. you watch it for changes using Obx or GetX widgets, (I guess you can call these two widgets "Observers".)

class Log2Page extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    Controller c = Get.put(Controller());
    // ↑ declare controller inside build method

    return Scaffold(
      body: SafeArea(
        child: Center(
          child: Column(
            mainAxisAlignment: MainAxisAlignment.spaceEvenly,
            children: [
              Obx(
                      () => Text('${c.log2.value}')
              ),
              RaisedButton(
                child: Text('Add +1'),
                onPressed: c.change,
              )
            ],
          ),
        ),
      ),
    );
  }
}

class Controller extends GetxController {
  RxInt log2 = 0.obs;

  void change() => log2.value++;
}

  1. 使用GetX时,您可能不需要StatefulWidget.GetxController存在于小部件的生命周期之外.状态存储在GetX控制器中(而不是存储在StatefulWidget中).
  2. GetX负责流&通过声明为 obs 的变量进行订阅,例如 count.obs log2.obs .当您想收听"时,或观察",请使用 Obx GetX 小部件.这些会自动侦听其子对象的 obs 更改,并在其更改时进行重建.
  1. You likely don't need a StatefulWidget when using GetX. A GetxController lives outside the lifecycle of widgets. State is stored in a GetX Controller (instead of in a StatefulWidget).
  2. GetX takes care of streams & subscriptions through variables you declare as obs, like count.obs and log2.obs. When you want to "listen" or "observe", use Obx or GetX widgets. These automatically listen to obs changes of its child and rebuild when it changes.

Obx与GetBuilder与GetX

class Log2Page extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    Controller c = Get.put(Controller());

    return Scaffold(
      body: SafeArea(
        child: Center(
          child: Column(
            mainAxisAlignment: MainAxisAlignment.spaceEvenly,
            children: [
              Obx(
                      () => Text('Obx: ${c.log2.value}')
              ),
              // ↓ requires manual controller.update() call
              GetBuilder<Controller>(
                builder: (_c) => Text('GetBuilder: ${_c.log2.value}'),
              ),
              // ↓ controller instantiated by Get widget
              GetX<Controller>(
                init: Controller(),
                builder: (_c) => Text('GetX: ${_c.log2.value}'),
              ),
              RaisedButton(
                child: Text('Add +1'),
                onPressed: c.change,
              ),
              RaisedButton(
                child: Text('Update GetBuilder'),
                onPressed: c.update, // rebuild GetBuilder widget
              ),
            ],
          ),
        ),
      ),
    );
  }
}

class Controller extends GetxController {
  RxInt log2 = 0.obs;

  void change() => log2.value++;
}

Obx

收听可观察的( obs )更改.控制器必须已经在其他地方声明/初始化才能使用.

Obx

Listens to observable (obs) changes. Controller needs to already be declared/initialized elsewhere to use.

收听可观察的( obs )更改.如果未在其他地方完成,则可以使用 init:构造函数参数来初始化控制器本身.可选参数.如果Controller已实例化,则可以安全地使用 init:.将连接到现有实例.

Listens to observable (obs) changes. Can initialize controller itself using init: constructor argument, if not done elsewhere. Optional argument. Safe to use init: if Controller already instantiated. Will connect to existing instance.

obs 的更改.必须由您手动调用 controller.update()进行重建.类似于 setState()调用.如果未在其他地方执行,则可以使用 init:参数初始化控制器本身.可选.

Does not listen to obs changes. Must be rebuilt manually by you, calling controller.update(). Similar to a setState() call. Can initialize controller itself using init: argument, if not done elsewhere. Optional.

这篇关于如何Flutter Getx将Obs绑定到Widget?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆