【问题标题】:How can I use the result of an async function in a Text in Flutter?如何在 Flutter 的文本中使用异步函数的结果?
【发布时间】:2021-12-19 04:38:43
【问题描述】:

我这周开始学习 Flutter。我正在尝试使用 Geolocator 包获取设备的位置,但我不习惯异步功能。我想在 AppBar 标题的文本中使用 position.latitude。我在代码中写了以显示正确的位置。下面是我的代码。

class HomeScreen extends StatelessWidget {
const HomeScreen({Key? key}) : super(key: key);

@override
Widget build(BuildContext context) {
  return Scaffold(
  appBar: buildAppBar(context),
);
}

AppBar buildAppBar(context) {
var position = null;

getCurrentPosition().then((position) => {position = position});

return AppBar(
    centerTitle: true,
    backgroundColor: kPrimaryColor,
    elevation: 0,
    toolbarHeight: MediaQuery.of(context).size.height * 0.07,
    title: Row(
      mainAxisAlignment: MainAxisAlignment.center,
      children: [
        IconButton(
          icon: const Icon(Icons.place),
          iconSize: 15,
          onPressed: () {},
        ),
        const Text(<position information goes here>,
            style: TextStyle(fontSize: 12)),
      ],
    ));
}

Future<Position> getCurrentPosition() async {
 Position position = await Geolocator.getCurrentPosition(
    desiredAccuracy: LocationAccuracy.high);

  return position;
  }
}

【问题讨论】:

  • 你遇到了什么错误?
  • 其实我有想法。您正在使用无状态小部件。因此,如果尝试更改您的文本,它将不会重新加载。除非您使用状态管理,否则您必须使用 Stateful 小部件在发生变化时重新加载屏幕。此外,您必须调用 setState() 来更新页面上的变量。

标签: flutter dart async-await


【解决方案1】:

我不知道你想怎么使用它。但我会在我理解这个问题时给出我的解决方案。 首先,将 StatelessWidget 改为 StatefulWidget。

然后您可以在 HomeScreen 类中定义位置变量并将当前位置设置为。 然后将此变量作为参数发送给 buildAppbar 函数:

AppBar buildAppBar(context, dynamic currentPos){...}

变量 currentPos 用于存储从名为 getCurrentPosition 的异步函数中获取的值。

Text 小部件仅接受 String 数据类型,因此您可以使用 currPos.toString() 方法或根据需要使用它。

从名为getCurrentPosition的异步函数中获取当前位置的值并将其赋值给位置变量 当创建小部件并将其发送到 buildAppbar 函数时,您可以在代码中执行以下操作。

*对不起 看图片中的代码。 我在手机上写了它,因为我现在没有圈,当我发布答案时,代码格式中会出现错误。因此,我将截取代码并将其添加到此处。

【讨论】:

    【解决方案2】:
    1. 您的页面必须是有状态的才能更改其状态。无状态小部件是静态的,您可以在小部件不变且用户不与屏幕交互时使用它们。
    2. 您必须调用 setState() 方法,这样您的页面才知道发生了一些变化。
    3. 稍后,如果您希望改进您​​的代码,请使用状态管理(MobX、GetX、Cubit、RxDart)而不是 setStates。使用 setState 时,widget-tree 下的所有小部件都会重新加载,因此会消耗更多 CPU 和 GPU。

    试试这样的:

    import 'package:flutter/material.dart';
    
    class HomeScreen extends StatefulWidget {
      const HomeScreen({Key? key}) : super(key: key);
    
      @override
      State<HomeScreen> createState() => _HomeScreenState();
    }
    
    class _HomeScreenState extends State<HomeScreen> {
      var position = null;
    
      @override
      void initState() {
        getCurrentPosition().then((position) {
          setState(() {
            position = position;
          });
        });
        super.initState();
      }
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: buildAppBar(context),
        );
      }
    
      AppBar buildAppBar(context) {
        return AppBar(
            centerTitle: true,
            backgroundColor: kPrimaryColor,
            elevation: 0,
            toolbarHeight: MediaQuery.of(context).size.height * 0.07,
            title: Row(
              mainAxisAlignment: MainAxisAlignment.center,
              children: [
                IconButton(
                  icon: const Icon(Icons.place),
                  iconSize: 15,
                  onPressed: () {},
                ),
                const Text(position ?? '', style: TextStyle(fontSize: 12)),
              ],
            ));
      }
    
      Future<Position> getCurrentPosition() async {
        Position position = await Geolocator.getCurrentPosition(
            desiredAccuracy: LocationAccuracy.high);
    
        return position;
      }
    }
    

    如果你有什么问题,给我反馈。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-08-01
      • 1970-01-01
      • 2021-12-19
      • 2020-06-03
      • 2022-01-11
      • 2012-03-14
      • 1970-01-01
      相关资源
      最近更新 更多