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
77b41ba8
Unverified
Commit
77b41ba8
authored
Aug 22, 2022
by
Greg Spencer
Committed by
GitHub
Aug 22, 2022
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Remove the FocusScopeNode in the navigator (#109702)
parent
d4eaf01a
Changes
6
Hide whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
97 additions
and
79 deletions
+97
-79
app.dart
packages/flutter/lib/src/widgets/app.dart
+18
-13
navigator.dart
packages/flutter/lib/src/widgets/navigator.dart
+30
-18
routes.dart
packages/flutter/lib/src/widgets/routes.dart
+5
-5
app_builder_test.dart
packages/flutter/test/material/app_builder_test.dart
+1
-1
debug_test.dart
packages/flutter/test/material/debug_test.dart
+8
-2
dropdown_test.dart
packages/flutter/test/material/dropdown_test.dart
+35
-40
No files found.
packages/flutter/lib/src/widgets/app.dart
View file @
77b41ba8
...
...
@@ -13,6 +13,7 @@ import 'banner.dart';
import
'basic.dart'
;
import
'binding.dart'
;
import
'default_text_editing_shortcuts.dart'
;
import
'focus_scope.dart'
;
import
'focus_traversal.dart'
;
import
'framework.dart'
;
import
'localizations.dart'
;
...
...
@@ -1625,19 +1626,23 @@ class _WidgetsAppState extends State<WidgetsApp> with WidgetsBindingObserver {
);
}
else
if
(
_usesNavigator
)
{
assert
(
_navigator
!=
null
);
routing
=
Navigator
(
restorationScopeId:
'nav'
,
key:
_navigator
,
initialRoute:
_initialRouteName
,
onGenerateRoute:
_onGenerateRoute
,
onGenerateInitialRoutes:
widget
.
onGenerateInitialRoutes
==
null
?
Navigator
.
defaultGenerateInitialRoutes
:
(
NavigatorState
navigator
,
String
initialRouteName
)
{
return
widget
.
onGenerateInitialRoutes
!(
initialRouteName
);
},
onUnknownRoute:
_onUnknownRoute
,
observers:
widget
.
navigatorObservers
!,
reportsRouteUpdateToEngine:
true
,
routing
=
FocusScope
(
debugLabel:
'Navigator Scope'
,
autofocus:
true
,
child:
Navigator
(
restorationScopeId:
'nav'
,
key:
_navigator
,
initialRoute:
_initialRouteName
,
onGenerateRoute:
_onGenerateRoute
,
onGenerateInitialRoutes:
widget
.
onGenerateInitialRoutes
==
null
?
Navigator
.
defaultGenerateInitialRoutes
:
(
NavigatorState
navigator
,
String
initialRouteName
)
{
return
widget
.
onGenerateInitialRoutes
!(
initialRouteName
);
},
onUnknownRoute:
_onUnknownRoute
,
observers:
widget
.
navigatorObservers
!,
reportsRouteUpdateToEngine:
true
,
),
);
}
else
if
(
_usesRouterWithConfig
)
{
routing
=
Router
<
Object
>.
withConfig
(
...
...
packages/flutter/lib/src/widgets/navigator.dart
View file @
77b41ba8
...
...
@@ -17,6 +17,7 @@ import 'basic.dart';
import
'binding.dart'
;
import
'focus_manager.dart'
;
import
'focus_scope.dart'
;
import
'focus_traversal.dart'
;
import
'framework.dart'
;
import
'heroes.dart'
;
import
'overlay.dart'
;
...
...
@@ -217,7 +218,7 @@ abstract class Route<T> {
TickerFuture
didPush
()
{
return
TickerFuture
.
complete
()..
then
<
void
>((
void
_
)
{
if
(
navigator
?.
widget
.
requestFocus
??
false
)
{
navigator
!.
focus
ScopeNode
.
requestFocus
();
navigator
!.
focus
Node
.
enclosingScope
?
.
requestFocus
();
}
});
}
...
...
@@ -233,11 +234,11 @@ abstract class Route<T> {
@mustCallSuper
void
didAdd
()
{
if
(
navigator
?.
widget
.
requestFocus
??
false
)
{
// This TickerFuture serves two purposes. First, we want to make sure
//
that animations triggered by other operations will finish before focusing the
//
navigator. Second, navigator.focusScope
Node might acquire more focused
// children in Route.install asynchronously. This TickerFuture will wait
for
// it to finish first.
// This TickerFuture serves two purposes. First, we want to make sure
that
//
animations triggered by other operations will finish before focusing
//
the navigator. Second, navigator.focus
Node might acquire more focused
// children in Route.install asynchronously. This TickerFuture will wait
//
for
it to finish first.
//
// The later case can be found when subclasses manage their own focus scopes.
// For example, ModalRoute creates a focus scope in its overlay entries. The
...
...
@@ -255,7 +256,7 @@ abstract class Route<T> {
// Since the reference to the navigator will be set to null after it is
// disposed, we have to do a null-safe operation in case that happens
// within the same frame when it is added.
navigator
?.
focus
ScopeNode
.
requestFocus
();
navigator
?.
focus
Node
.
enclosingScope
?
.
requestFocus
();
});
}
}
...
...
@@ -3207,8 +3208,15 @@ class NavigatorState extends State<Navigator> with TickerProviderStateMixin, Res
final
Queue
<
_NavigatorObservation
>
_observedRouteAdditions
=
Queue
<
_NavigatorObservation
>();
final
Queue
<
_NavigatorObservation
>
_observedRouteDeletions
=
Queue
<
_NavigatorObservation
>();
/// The [FocusScopeNode] for the [FocusScope] that encloses the routes.
final
FocusScopeNode
focusScopeNode
=
FocusScopeNode
(
debugLabel:
'Navigator Scope'
);
/// The [FocusScopeNode] for the [FocusScope] that encloses the topmost navigator.
@Deprecated
(
'Use focusNode.enclosingScope! instead. '
'This feature was deprecated after v3.1.0-0.0.pre.'
)
FocusScopeNode
get
focusScopeNode
=>
focusNode
.
enclosingScope
!;
/// The [FocusNode] for the [Focus] that encloses the routes.
final
FocusNode
focusNode
=
FocusNode
(
debugLabel:
'Navigator'
);
bool
_debugLocked
=
false
;
// used to prevent re-entrant calls to push, pop, and friends
...
...
@@ -3531,7 +3539,7 @@ class NavigatorState extends State<Navigator> with TickerProviderStateMixin, Res
return
true
;
}());
_updateHeroController
(
null
);
focus
Scope
Node
.
dispose
();
focusNode
.
dispose
();
for
(
final
_RouteEntry
entry
in
_history
)
{
entry
.
dispose
();
}
...
...
@@ -5226,14 +5234,18 @@ class NavigatorState extends State<Navigator> with TickerProviderStateMixin, Res
onPointerCancel:
_handlePointerUpOrCancel
,
child:
AbsorbPointer
(
absorbing:
false
,
// it's mutated directly by _cancelActivePointers above
child:
FocusScope
(
node:
focusScopeNode
,
autofocus:
true
,
child:
UnmanagedRestorationScope
(
bucket:
bucket
,
child:
Overlay
(
key:
_overlayKey
,
initialEntries:
overlay
==
null
?
_allRouteOverlayEntries
.
toList
(
growable:
false
)
:
const
<
OverlayEntry
>[],
child:
FocusTraversalGroup
(
child:
Focus
(
focusNode:
focusNode
,
autofocus:
true
,
skipTraversal:
true
,
includeSemantics:
false
,
child:
UnmanagedRestorationScope
(
bucket:
bucket
,
child:
Overlay
(
key:
_overlayKey
,
initialEntries:
overlay
==
null
?
_allRouteOverlayEntries
.
toList
(
growable:
false
)
:
const
<
OverlayEntry
>[],
),
),
),
),
...
...
packages/flutter/lib/src/widgets/routes.dart
View file @
77b41ba8
...
...
@@ -819,7 +819,7 @@ class _ModalScopeState<T> extends State<_ModalScope<T>> {
];
_listenable
=
Listenable
.
merge
(
animations
);
if
(
widget
.
route
.
isCurrent
&&
_shouldRequestFocus
)
{
widget
.
route
.
navigator
!.
focus
ScopeNode
.
setFirstFocus
(
focusScopeNode
);
widget
.
route
.
navigator
!.
focus
Node
.
enclosingScope
?
.
setFirstFocus
(
focusScopeNode
);
}
}
...
...
@@ -828,7 +828,7 @@ class _ModalScopeState<T> extends State<_ModalScope<T>> {
super
.
didUpdateWidget
(
oldWidget
);
assert
(
widget
.
route
==
oldWidget
.
route
);
if
(
widget
.
route
.
isCurrent
&&
_shouldRequestFocus
)
{
widget
.
route
.
navigator
!.
focus
ScopeNode
.
setFirstFocus
(
focusScopeNode
);
widget
.
route
.
navigator
!.
focus
Node
.
enclosingScope
?
.
setFirstFocus
(
focusScopeNode
);
}
}
...
...
@@ -863,7 +863,7 @@ class _ModalScopeState<T> extends State<_ModalScope<T>> {
// and route.offstage.
void
_routeSetState
(
VoidCallback
fn
)
{
if
(
widget
.
route
.
isCurrent
&&
!
_shouldIgnoreFocusRequest
&&
_shouldRequestFocus
)
{
widget
.
route
.
navigator
!.
focus
ScopeNode
.
setFirstFocus
(
focusScopeNode
);
widget
.
route
.
navigator
!.
focus
Node
.
enclosingScope
?
.
setFirstFocus
(
focusScopeNode
);
}
setState
(
fn
);
}
...
...
@@ -1213,7 +1213,7 @@ abstract class ModalRoute<T> extends TransitionRoute<T> with LocalHistoryRoute<T
@override
TickerFuture
didPush
()
{
if
(
_scopeKey
.
currentState
!=
null
&&
navigator
!.
widget
.
requestFocus
)
{
navigator
!.
focus
ScopeNode
.
setFirstFocus
(
_scopeKey
.
currentState
!.
focusScopeNode
);
navigator
!.
focus
Node
.
enclosingScope
?
.
setFirstFocus
(
_scopeKey
.
currentState
!.
focusScopeNode
);
}
return
super
.
didPush
();
}
...
...
@@ -1221,7 +1221,7 @@ abstract class ModalRoute<T> extends TransitionRoute<T> with LocalHistoryRoute<T
@override
void
didAdd
()
{
if
(
_scopeKey
.
currentState
!=
null
&&
navigator
!.
widget
.
requestFocus
)
{
navigator
!.
focus
ScopeNode
.
setFirstFocus
(
_scopeKey
.
currentState
!.
focusScopeNode
);
navigator
!.
focus
Node
.
enclosingScope
?
.
setFirstFocus
(
_scopeKey
.
currentState
!.
focusScopeNode
);
}
super
.
didAdd
();
}
...
...
packages/flutter/test/material/app_builder_test.dart
View file @
77b41ba8
...
...
@@ -17,7 +17,7 @@ void main() {
log
.
add
(
'build'
);
expect
(
Theme
.
of
(
context
).
primaryColor
,
Colors
.
green
);
expect
(
Directionality
.
of
(
context
),
TextDirection
.
ltr
);
expect
(
child
,
isA
<
Navigator
>());
expect
(
child
,
isA
<
FocusScope
>());
return
const
Placeholder
();
},
);
...
...
packages/flutter/test/material/debug_test.dart
View file @
77b41ba8
...
...
@@ -156,12 +156,18 @@ void main() {
' Overlay-[LabeledGlobalKey<OverlayState>#00000]
\n
'
' UnmanagedRestorationScope
\n
'
' _FocusMarker
\n
'
' Semantics
\n
'
' FocusScope
\n
'
' Focus
\n
'
' _FocusMarker
\n
'
' Focus
\n
'
' _FocusTraversalGroupMarker
\n
'
' FocusTraversalGroup
\n
'
' AbsorbPointer
\n
'
' Listener
\n
'
' HeroControllerScope
\n
'
' Navigator-[GlobalObjectKey<NavigatorState> _WidgetsAppState#00000]
\n
'
' _FocusMarker
\n
'
' Semantics
\n
'
' FocusScope
\n
'
' DefaultSelectionStyle
\n
'
' IconTheme
\n
'
' IconTheme
\n
'
...
...
packages/flutter/test/material/dropdown_test.dart
View file @
77b41ba8
...
...
@@ -1326,53 +1326,49 @@ void main() {
TestSemantics
.
rootChild
(
children:
<
TestSemantics
>[
TestSemantics
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
,
SemanticsFlag
.
namesRoute
,
],
label:
'Popup menu'
,
children:
<
TestSemantics
>[
TestSemantics
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
,
SemanticsFlag
.
namesRoute
,
],
label:
'Popup menu'
,
children:
<
TestSemantics
>[
TestSemantics
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
hasImplicitScrolling
,
],
children:
<
TestSemantics
>[
TestSemantics
(
label:
'one'
,
textDirection:
TextDirection
.
ltr
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
hasImplicitScrolling
,
],
children:
<
TestSemantics
>[
TestSemantics
(
label:
'one'
,
textDirection:
TextDirection
.
ltr
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isFocused
,
SemanticsFlag
.
isFocusable
,
],
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
),
TestSemantics
(
label:
'two'
,
textDirection:
TextDirection
.
ltr
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isFocusable
],
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
),
TestSemantics
(
label:
'three'
,
textDirection:
TextDirection
.
ltr
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isFocusable
],
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
),
TestSemantics
(
label:
'four'
,
textDirection:
TextDirection
.
ltr
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isFocusable
],
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
),
SemanticsFlag
.
isFocused
,
SemanticsFlag
.
isFocusable
,
],
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
),
TestSemantics
(
label:
'two'
,
textDirection:
TextDirection
.
ltr
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isFocusable
],
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
),
TestSemantics
(
label:
'three'
,
textDirection:
TextDirection
.
ltr
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isFocusable
],
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
),
TestSemantics
(
label:
'four'
,
textDirection:
TextDirection
.
ltr
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isFocusable
],
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
),
],
),
...
...
@@ -1380,7 +1376,6 @@ void main() {
),
],
),
TestSemantics
(),
],
),
],
...
...
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