找不到无方向性小部件

83

我正在尝试在flutter中创建一个简单的布局,但一直收到如下错误信息:

构建Text("Deliver features faster", textAlign: center)时出现以下断言错误: 没有找到Directionality widget。

我认为问题可能出在TextDirection类属性上,但我一直没有找到它。

这是我的代码:

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

void main(){

  runApp( new MyHome());
}

class MyHome extends StatelessWidget{

  @override

  Widget build(BuildContext context) {
    // TODO: implement build
    return new Material(
      child: new Container(
        color: Colors.red,
        margin: const EdgeInsets.all(5.0),
        child: new Row(
          children: <Widget>[
            new Expanded(
              child: new Text('Deliver features faster', textAlign: TextAlign.center),
            ),
            new Expanded(
              child: new Text('Craft beautiful UIs', textAlign: TextAlign.center),
            ),
            new Expanded(
              child: new FittedBox(
                fit: BoxFit.contain, // otherwise the logo will be tiny
                child: const FlutterLogo(),
              ),
            ),
          ],
        )
      ),
    );
  }
}

这里是错误的完整堆栈跟踪:

The following assertion was thrown building Text("Deliver features faster", textAlign: center):
No Directionality widget found.
RichText widgets require a Directionality widget ancestor.
The specific widget that could not find a Directionality ancestor was:
  RichText(textAlign: center, softWrap: wrapping at box width, maxLines: unlimited, text: "Deliver
  features faster")
The ownership chain for the affected widget is:
  RichText ← Text ← Expanded ← Row ← DecoratedBox ← Padding ← Container ← DefaultTextStyle ←
  AnimatedDefaultTextStyle ← _InkFeatures-[GlobalKey#978b7 ink renderer] ← ⋯
Typically, the Directionality widget is introduced by the MaterialApp or WidgetsApp widget at the
top of your application widget tree. It determines the ambient reading direction and is used, for
example, to determine how to lay out text, how to interpret "start" and "end" values, and to resolve
EdgeInsetsDirectional, AlignmentDirectional, and other *Directional objects.
When the exception was thrown, this was the stack:
#0      debugCheckHasDirectionality.<anonymous closure> (package:flutter/src/widgets/debug.dart:223:7)
#1      debugCheckHasDirectionality (package:flutter/src/widgets/debug.dart:239:4)
#2      RichText.createRenderObject (package:flutter/src/widgets/basic.dart:4245:37)
#3      RenderObjectElement.mount (package:flutter/src/widgets/framework.dart:4259:28)
#4      Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#5      Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#6      ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#7      Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#8      ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#9      ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#10     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#11     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#12     ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#13     Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#14     ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#15     ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#16     ParentDataElement.mount (package:flutter/src/widgets/framework.dart:3938:16)
#17     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#18     MultiChildRenderObjectElement.mount (package:flutter/src/widgets/framework.dart:4738:32)
#19     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#20     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#21     SingleChildRenderObjectElement.mount (package:flutter/src/widgets/framework.dart:4633:14)
#22     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#23     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#24     SingleChildRenderObjectElement.mount (package:flutter/src/widgets/framework.dart:4633:14)
#25     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#26     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#27     ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#28     Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#29     ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#30     ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#31     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#32     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#33     ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#34     Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#35     ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#36     ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#37     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#38     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#39     ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#40     Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#41     ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#42     StatefulElement._firstBuild (package:flutter/src/widgets/framework.dart:3752:22)
#43     ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#44     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#45     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#46     SingleChildRenderObjectElement.mount (package:flutter/src/widgets/framework.dart:4633:14)
#47     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#48     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#49     ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#50     Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#51     ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#52     ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#53     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#54     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#55     SingleChildRenderObjectElement.mount (package:flutter/src/widgets/framework.dart:4633:14)
#56     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#57     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#58     ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#59     Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#60     ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#61     StatefulElement._firstBuild (package:flutter/src/widgets/framework.dart:3752:22)
#62     ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#63     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#64     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#65     ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#66     Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#67     ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#68     StatefulElement._firstBuild (package:flutter/src/widgets/framework.dart:3752:22)
#69     ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#70     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#71     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#72     ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3636:16)
#73     Element.rebuild (package:flutter/src/widgets/framework.dart:3478:5)
#74     ComponentElement._firstBuild (package:flutter/src/widgets/framework.dart:3605:5)
#75     ComponentElement.mount (package:flutter/src/widgets/framework.dart:3600:5)
#76     Element.inflateWidget (package:flutter/src/widgets/framework.dart:2890:14)
#77     Element.updateChild (package:flutter/src/widgets/framework.dart:2693:12)
#78     RenderObjectToWidgetElement._rebuild (package:flutter/src/widgets/binding.dart:852:16)
#79     RenderObjectToWidgetElement.mount (package:flutter/src/widgets/binding.dart:823:5)
#80     RenderObjectToWidgetAdapter.attachToRenderTree.<anonymous closure> (package:flutter/src/widgets/binding.dart:769:17)
#81     BuildOwner.buildScope (package:flutter/src/widgets/framework.dart:2205:19)
#82     RenderObjectToWidgetAdapter.attachToRenderTree (package:flutter/src/widgets/binding.dart:768:13)
#83     BindingBase&GestureBinding&ServicesBinding&SchedulerBinding&PaintingBinding&RendererBinding&WidgetsBinding.attachRootWidget (package:flutter/src/widgets/binding.dart:657:7)
#84     runApp (package:flutter/src/widgets/binding.dart:699:7)
#85     main (/data/user/0/com.yourcompany.flutterproject/cache/flutter_projectENWZDI/flutter_project/lib/main.dart:6:3)
#86     _startIsolate.<anonymous closure> (dart:isolate-patch/dart:isolate/isolate_patch.dart:279)
#87     _RawReceivePortImpl._handleMessage (dart:isolate-patch/dart:isolate/isolate_patch.dart:165)
════════════════════════════════════════════════════════════════════════════════════════════════════
Another exception was thrown: No Directionality widget found.
Another exception was thrown: Horizontal RenderFlex with multiple children has a null textDirection, so the layout order is undefined.
Another exception was thrown: 'package:flutter/src/rendering/box.dart': Failed assertion: line 1446 pos 12: 'hasSize': is not true.
uid=10079(com.yourcompany.flutterproject) Thread-5 identical 2 lines
Another exception was thrown: 'package:flutter/src/rendering/box.dart': Failed assertion: line 1446 pos 12: 'hasSize': is not true.
Another exception was thrown: 'package:flutter/src/rendering/proxy_box.dart': Failed assertion: line 1564 pos 12: 'hasSize': is not true.

请发布您的想法,并进一步解释您所期望的行为应该是什么。 - rak007
5个回答

98

Flutter不知道文本是从左到右还是从右到左,所以你需要明确告诉它textDirection

Text("Hello", textDirection: TextDirection.ltr)

或者你可以使用Directionality小部件将文本包裹起来。
Directionality(
          textDirection: TextDirection.ltr,
          child: Text('Hello')

而这个目的是:

一个小部件,用于确定文本的环境方向性和对文本方向敏感的渲染对象。

在MaterialApp小部件的范围内,Text小部件不需要明确指定书写方向,因为小部件和材料库的默认本地化是LTR(从左到右)。


62

如果您不使用MaterialApp,则需要自行将应用程序包装到某些小部件中。

import 'dart:ui' as ui;
...
runApp(
    new MediaQuery(
        data: new MediaQueryData.fromWindow(ui.window),
        child: new Directionality(
            textDirection: TextDirection.rtl,
            child: new MyHome())))

1
TextDirection.rtl 这行代码有什么用? - Ravindra Bhanderi
“Directionality”小部件需要设置方向。这是该小部件的主要目的。 - Günter Zöchbauer
这个答案是正确的,所以我将其纠正了,但现在我发现那个人复制并粘贴了你的答案。 - Ravindra Bhanderi
我得到了未定义的名称ui。 - Pinkesh Darji
1
你需要添加 import 'dart:ui' as ui; - Günter Zöchbauer

35

如果您没有在树结构的根级别使用MaterialAppWidgetsApp,则会出现此错误。

解决方案:

void main() {
  runApp(
    MaterialApp(home: MyHome()), // use MaterialApp
  );
}

class MyHome extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold( // use Scaffold also in order to provide material app widgets
      body: Center(child: Text("Something")),
    );
  }
}

5
问题不在于您没有将小部件包装到MaterialApp中。正如文档所说,此错误是由于嵌套相同类型的小部件引起的,例如将Row嵌套到Row中,Column嵌套到Column中或将Column嵌套到ListView中,因此出现了无界约束的小部件无法识别方向。
因此,为避免这种问题,使用Flexible或Expanded来识别剩余空间。
在您的情况下,您可以简单地将crossAxisAlignment设置为start以应用于Row小部件。
有关更多信息,请访问documentation页面。

0
这不是对原问题的解决方案,而是针对类似的其他情况。
完全同意@CopsOnRoad的答案。除此之外,还有一些情况下你必须使用MaterialApp.router选项,而不是MaterialApp。例如,当我们使用go_router插件时,可能会遇到这种情况。
对于应用程序开发中的正常路径,你不会遇到使用MaterialApp.router的这个问题。如果你尝试为这种情况编写WidgetTest,你将会遇到这个错误。在这种情况下,其中一个解决方案是:
  testWidgets('Description', (widgetTester) async {
    await widgetTester.pumpWidget(const MaterialApp(
      home: YourScreen(),
    ));

    // rest of the code goes here
  });

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接