Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Sign in
Toggle navigation
F
Front-End
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
abdullh.alsoleman
Front-End
Commits
67881172
Unverified
Commit
67881172
authored
Jun 03, 2020
by
Ian Hickson
Committed by
GitHub
Jun 03, 2020
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Error message improvements (#58204)
parent
1a9530af
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
98 additions
and
4 deletions
+98
-4
alignment.dart
packages/flutter/lib/src/painting/alignment.dart
+2
-2
framework.dart
packages/flutter/lib/src/widgets/framework.dart
+28
-1
framework_test.dart
packages/flutter/test/widgets/framework_test.dart
+68
-1
No files found.
packages/flutter/lib/src/painting/alignment.dart
View file @
67881172
...
...
@@ -525,7 +525,7 @@ class AlignmentDirectional extends AlignmentGeometry {
@override
Alignment
resolve
(
TextDirection
direction
)
{
assert
(
direction
!=
null
);
assert
(
direction
!=
null
,
'Cannot resolve
$runtimeType
without a TextDirection.'
);
switch
(
direction
)
{
case
TextDirection
.
rtl
:
return
Alignment
(-
start
,
y
);
...
...
@@ -621,7 +621,7 @@ class _MixedAlignment extends AlignmentGeometry {
@override
Alignment
resolve
(
TextDirection
direction
)
{
assert
(
direction
!=
null
);
assert
(
direction
!=
null
,
'Cannot resolve
$runtimeType
without a TextDirection.'
);
switch
(
direction
)
{
case
TextDirection
.
rtl
:
return
Alignment
(
_x
-
_start
,
_y
);
...
...
packages/flutter/lib/src/widgets/framework.dart
View file @
67881172
...
...
@@ -2627,7 +2627,34 @@ class BuildOwner {
while
(
index
<
dirtyCount
)
{
assert
(
_dirtyElements
[
index
]
!=
null
);
assert
(
_dirtyElements
[
index
].
_inDirtyList
);
assert
(!
_dirtyElements
[
index
].
_active
||
_dirtyElements
[
index
].
_debugIsInScope
(
context
));
assert
(()
{
if
(
_dirtyElements
[
index
].
_active
&&
!
_dirtyElements
[
index
].
_debugIsInScope
(
context
))
{
throw
FlutterError
.
fromParts
(<
DiagnosticsNode
>[
ErrorSummary
(
'Tried to build dirty widget in the wrong build scope.'
),
ErrorDescription
(
'A widget which was marked as dirty and is still active was scheduled to be built, '
'but the current build scope unexpectedly does not contain that widget.'
,
),
ErrorHint
(
'Sometimes this is detected when an element is removed from the widget tree, but the '
'element somehow did not get marked as inactive. In that case, it might be caused by '
'an ancestor element failing to implement visitChildren correctly, thus preventing '
'some or all of its descendants from being correctly deactivated.'
,
),
DiagnosticsProperty
<
Element
>(
'The root of the build scope was'
,
context
,
style:
DiagnosticsTreeStyle
.
errorProperty
,
),
DiagnosticsProperty
<
Element
>(
'The offending element (which does not appear to be a descendant of the root of the build scope) was'
,
_dirtyElements
[
index
],
style:
DiagnosticsTreeStyle
.
errorProperty
,
),
]);
}
return
true
;
}());
try
{
_dirtyElements
[
index
].
rebuild
();
}
catch
(
e
,
stack
)
{
...
...
packages/flutter/test/widgets/framework_test.dart
View file @
67881172
...
...
@@ -1427,6 +1427,74 @@ void main() {
expect
(
debugDoingBuildOnDidUnmountRenderObject
,
isFalse
);
});
});
testWidgets
(
'A widget whose element has an invalid visitChildren implementation triggers a useful error message'
,
(
WidgetTester
tester
)
async
{
final
GlobalKey
key
=
GlobalKey
();
await
tester
.
pumpWidget
(
Container
(
child:
_WidgetWithNoVisitChildren
(
_StatefulLeaf
(
key:
key
))));
(
key
.
currentState
as
_StatefulLeafState
).
markNeedsBuild
();
await
tester
.
pumpWidget
(
Container
());
final
dynamic
exception
=
tester
.
takeException
();
expect
(
exception
.
message
,
equalsIgnoringHashCodes
(
'Tried to build dirty widget in the wrong build scope.
\n
'
'A widget which was marked as dirty and is still active was scheduled to be built, '
'but the current build scope unexpectedly does not contain that widget.
\n
'
'Sometimes this is detected when an element is removed from the widget tree, but '
'the element somehow did not get marked as inactive. In that case, it might be '
'caused by an ancestor element failing to implement visitChildren correctly, thus '
'preventing some or all of its descendants from being correctly deactivated.
\n
'
'The root of the build scope was:
\n
'
' [root]
\n
'
'The offending element (which does not appear to be a descendant of the root of '
'the build scope) was:
\n
'
' _StatefulLeaf-[GlobalKey#00000]'
)
);
});
}
class
_WidgetWithNoVisitChildren
extends
StatelessWidget
{
const
_WidgetWithNoVisitChildren
(
this
.
child
,
{
Key
key
})
:
super
(
key:
key
);
final
Widget
child
;
@override
Widget
build
(
BuildContext
context
)
=>
child
;
@override
_WidgetWithNoVisitChildrenElement
createElement
()
=>
_WidgetWithNoVisitChildrenElement
(
this
);
}
class
_WidgetWithNoVisitChildrenElement
extends
StatelessElement
{
_WidgetWithNoVisitChildrenElement
(
_WidgetWithNoVisitChildren
widget
):
super
(
widget
);
@override
void
visitChildren
(
ElementVisitor
visitor
)
{
// This implementation is intentionally buggy, to test that an error message is
// shown when this situation occurs.
// The superclass has the correct implementation (calling `visitor(_child)`), so
// we don't call it here.
}
}
class
_StatefulLeaf
extends
StatefulWidget
{
const
_StatefulLeaf
({
Key
key
})
:
super
(
key:
key
);
@override
State
<
_StatefulLeaf
>
createState
()
=>
_StatefulLeafState
();
}
class
_StatefulLeafState
extends
State
<
_StatefulLeaf
>
{
void
markNeedsBuild
()
{
setState
(()
{
});
}
@override
Widget
build
(
BuildContext
context
)
{
return
const
SizedBox
.
shrink
();
}
}
class
Decorate
extends
StatefulWidget
{
...
...
@@ -1503,7 +1571,6 @@ class NullChildElement extends Element {
bool
get
debugDoingBuild
=>
throw
UnimplementedError
();
}
class
DirtyElementWithCustomBuildOwner
extends
Element
{
DirtyElementWithCustomBuildOwner
(
BuildOwner
buildOwner
,
Widget
widget
)
:
_owner
=
buildOwner
,
super
(
widget
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment