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
034a663d
Unverified
Commit
034a663d
authored
Apr 20, 2018
by
Jonah Williams
Committed by
GitHub
Apr 20, 2018
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Semantics object support for edge triggered semantics (#16081)
Semantics object support for edge triggered semantics
parent
d05bc9c0
Changes
26
Hide whitespace changes
Inline
Side-by-side
Showing
26 changed files
with
650 additions
and
162 deletions
+650
-162
pesto_demo.dart
examples/flutter_gallery/lib/demo/pesto_demo.dart
+26
-23
route.dart
packages/flutter/lib/src/cupertino/route.dart
+5
-1
app_bar.dart
packages/flutter/lib/src/material/app_bar.dart
+9
-0
dialog.dart
packages/flutter/lib/src/material/dialog.dart
+92
-24
drawer.dart
packages/flutter/lib/src/material/drawer.dart
+34
-5
flexible_space_bar.dart
packages/flutter/lib/src/material/flexible_space_bar.dart
+17
-1
page.dart
packages/flutter/lib/src/material/page.dart
+6
-2
popup_menu.dart
packages/flutter/lib/src/material/popup_menu.dart
+33
-4
custom_paint.dart
packages/flutter/lib/src/rendering/custom_paint.dart
+6
-0
proxy_box.dart
packages/flutter/lib/src/rendering/proxy_box.dart
+30
-0
semantics.dart
packages/flutter/lib/src/semantics/semantics.dart
+40
-0
basic.dart
packages/flutter/lib/src/widgets/basic.dart
+12
-0
date_picker_test.dart
packages/flutter/test/material/date_picker_test.dart
+4
-1
dialog_test.dart
packages/flutter/test/material/dialog_test.dart
+49
-0
floating_action_button_test.dart
...es/flutter/test/material/floating_action_button_test.dart
+14
-7
popup_menu_test.dart
packages/flutter/test/material/popup_menu_test.dart
+36
-1
tooltip_test.dart
packages/flutter/test/material/tooltip_test.dart
+23
-10
user_accounts_drawer_header_test.dart
...utter/test/material/user_accounts_drawer_header_test.dart
+38
-28
custom_painter_test.dart
packages/flutter/test/widgets/custom_painter_test.dart
+3
-5
drawer_test.dart
packages/flutter/test/widgets/drawer_test.dart
+38
-0
editable_text_test.dart
packages/flutter/test/widgets/editable_text_test.dart
+32
-21
navigator_test.dart
packages/flutter/test/widgets/navigator_test.dart
+50
-0
semantics_test.dart
packages/flutter/test/widgets/semantics_test.dart
+5
-5
semantics_tester_generateTestSemanticsExpressionForCurrentSemanticsTree_test.dart
...eTestSemanticsExpressionForCurrentSemanticsTree_test.dart
+25
-19
simple_semantics_test.dart
packages/flutter/test/widgets/simple_semantics_test.dart
+14
-5
sliver_semantics_test.dart
packages/flutter/test/widgets/sliver_semantics_test.dart
+9
-0
No files found.
examples/flutter_gallery/lib/demo/pesto_demo.dart
View file @
034a663d
...
@@ -96,7 +96,7 @@ class _RecipeGridPageState extends State<RecipeGridPage> {
...
@@ -96,7 +96,7 @@ class _RecipeGridPageState extends State<RecipeGridPage> {
_buildBody
(
context
,
statusBarHeight
),
_buildBody
(
context
,
statusBarHeight
),
],
],
),
),
)
)
,
);
);
}
}
...
@@ -215,30 +215,33 @@ class _PestoLogoState extends State<PestoLogo> {
...
@@ -215,30 +215,33 @@ class _PestoLogoState extends State<PestoLogo> {
@override
@override
Widget
build
(
BuildContext
context
)
{
Widget
build
(
BuildContext
context
)
{
return
new
Transform
(
return
new
Semantics
(
transform:
new
Matrix4
.
identity
()..
scale
(
widget
.
height
/
kLogoHeight
),
namesRoute:
true
,
alignment:
Alignment
.
topCenter
,
child:
new
Transform
(
child:
new
SizedBox
(
transform:
new
Matrix4
.
identity
()..
scale
(
widget
.
height
/
kLogoHeight
),
width:
kLogoWidth
,
alignment:
Alignment
.
topCenter
,
child:
new
Stack
(
child:
new
SizedBox
(
overflow:
Overflow
.
visible
,
width:
kLogoWidth
,
children:
<
Widget
>[
child:
new
Stack
(
new
Positioned
.
fromRect
(
overflow:
Overflow
.
visible
,
rect:
_imageRectTween
.
lerp
(
widget
.
t
),
children:
<
Widget
>[
child:
new
Image
.
asset
(
new
Positioned
.
fromRect
(
_kSmallLogoImage
,
rect:
_imageRectTween
.
lerp
(
widget
.
t
),
package:
_kGalleryAssetsPackage
,
child:
new
Image
.
asset
(
fit:
BoxFit
.
contain
,
_kSmallLogoImage
,
package:
_kGalleryAssetsPackage
,
fit:
BoxFit
.
contain
,
),
),
),
),
new
Positioned
.
fromRect
(
new
Positioned
.
fromRect
(
rect:
_textRectTween
.
lerp
(
widget
.
t
),
rect:
_textRectTween
.
lerp
(
widget
.
t
),
child:
new
Opacity
(
child:
new
Opacity
(
opacity:
_textOpacity
.
transform
(
widget
.
t
),
opacity:
_textOpacity
.
transform
(
widget
.
t
),
child:
new
Text
(
'PESTO'
,
style:
titleStyle
,
textAlign:
TextAlign
.
center
),
child:
new
Text
(
'PESTO'
,
style:
titleStyle
,
textAlign:
TextAlign
.
center
),
),
),
),
)
,
]
,
]
,
)
,
),
),
),
),
);
);
...
...
packages/flutter/lib/src/cupertino/route.dart
View file @
034a663d
...
@@ -237,7 +237,11 @@ class CupertinoPageRoute<T> extends PageRoute<T> {
...
@@ -237,7 +237,11 @@ class CupertinoPageRoute<T> extends PageRoute<T> {
@override
@override
Widget
buildPage
(
BuildContext
context
,
Animation
<
double
>
animation
,
Animation
<
double
>
secondaryAnimation
)
{
Widget
buildPage
(
BuildContext
context
,
Animation
<
double
>
animation
,
Animation
<
double
>
secondaryAnimation
)
{
final
Widget
result
=
builder
(
context
);
final
Widget
result
=
new
Semantics
(
scopesRoute:
true
,
explicitChildNodes:
true
,
child:
builder
(
context
),
);
assert
(()
{
assert
(()
{
if
(
result
==
null
)
{
if
(
result
==
null
)
{
throw
new
FlutterError
(
throw
new
FlutterError
(
...
...
packages/flutter/lib/src/material/app_bar.dart
View file @
034a663d
...
@@ -383,6 +383,15 @@ class _AppBarState extends State<AppBar> {
...
@@ -383,6 +383,15 @@ class _AppBarState extends State<AppBar> {
Widget
title
=
widget
.
title
;
Widget
title
=
widget
.
title
;
if
(
title
!=
null
)
{
if
(
title
!=
null
)
{
switch
(
defaultTargetPlatform
)
{
case
TargetPlatform
.
android
:
case
TargetPlatform
.
fuchsia
:
title
=
new
Semantics
(
namesRoute:
true
,
child:
title
);
break
;
case
TargetPlatform
.
iOS
:
break
;
}
title
=
new
DefaultTextStyle
(
title
=
new
DefaultTextStyle
(
style:
centerStyle
,
style:
centerStyle
,
softWrap:
false
,
softWrap:
false
,
...
...
packages/flutter/lib/src/material/dialog.dart
View file @
034a663d
...
@@ -166,6 +166,7 @@ class AlertDialog extends StatelessWidget {
...
@@ -166,6 +166,7 @@ class AlertDialog extends StatelessWidget {
this
.
content
,
this
.
content
,
this
.
contentPadding
:
const
EdgeInsets
.
fromLTRB
(
24.0
,
20.0
,
24.0
,
24.0
),
this
.
contentPadding
:
const
EdgeInsets
.
fromLTRB
(
24.0
,
20.0
,
24.0
,
24.0
),
this
.
actions
,
this
.
actions
,
this
.
semanticLabel
,
})
:
assert
(
contentPadding
!=
null
),
})
:
assert
(
contentPadding
!=
null
),
super
(
key:
key
);
super
(
key:
key
);
...
@@ -216,18 +217,41 @@ class AlertDialog extends StatelessWidget {
...
@@ -216,18 +217,41 @@ class AlertDialog extends StatelessWidget {
/// from the [actions].
/// from the [actions].
final
List
<
Widget
>
actions
;
final
List
<
Widget
>
actions
;
/// The semantic label of the dialog used by accessibility frameworks to
/// announce screen transitions when the dialog is opened and closed.
///
/// If this label is not provided, a semantic label will be infered from the
/// [title] if it is not null. If there is no title, the label will be taken
/// from [MaterialLocalizations.alertDialogLabel].
///
/// See also:
///
/// * [SemanticsConfiguration.isRouteName], for a description of how this
/// value is used.
final
String
semanticLabel
;
@override
@override
Widget
build
(
BuildContext
context
)
{
Widget
build
(
BuildContext
context
)
{
final
List
<
Widget
>
children
=
<
Widget
>[];
final
List
<
Widget
>
children
=
<
Widget
>[];
String
label
=
semanticLabel
;
if
(
title
!=
null
)
{
if
(
title
!=
null
)
{
children
.
add
(
new
Padding
(
children
.
add
(
new
Padding
(
padding:
titlePadding
??
new
EdgeInsets
.
fromLTRB
(
24.0
,
24.0
,
24.0
,
content
==
null
?
20.0
:
0.0
),
padding:
titlePadding
??
new
EdgeInsets
.
fromLTRB
(
24.0
,
24.0
,
24.0
,
content
==
null
?
20.0
:
0.0
),
child:
new
DefaultTextStyle
(
child:
new
DefaultTextStyle
(
style:
Theme
.
of
(
context
).
textTheme
.
title
,
style:
Theme
.
of
(
context
).
textTheme
.
title
,
child:
title
,
child:
new
Semantics
(
child:
title
,
namesRoute:
true
)
,
),
),
));
));
}
else
{
switch
(
defaultTargetPlatform
)
{
case
TargetPlatform
.
iOS
:
label
=
semanticLabel
;
break
;
case
TargetPlatform
.
android
:
case
TargetPlatform
.
fuchsia
:
label
=
semanticLabel
??
MaterialLocalizations
.
of
(
context
)?.
alertDialogLabel
;
}
}
}
if
(
content
!=
null
)
{
if
(
content
!=
null
)
{
...
@@ -250,15 +274,22 @@ class AlertDialog extends StatelessWidget {
...
@@ -250,15 +274,22 @@ class AlertDialog extends StatelessWidget {
));
));
}
}
return
new
Dialog
(
Widget
dialogChild
=
new
IntrinsicWidth
(
child:
new
IntrinsicWidth
(
child:
new
Column
(
child:
new
Column
(
mainAxisSize:
MainAxisSize
.
min
,
mainAxisSize:
MainAxisSize
.
min
,
crossAxisAlignment:
CrossAxisAlignment
.
stretch
,
crossAxisAlignment:
CrossAxisAlignment
.
stretch
,
children:
children
,
children:
children
,
),
),
),
);
);
if
(
label
!=
null
)
dialogChild
=
new
Semantics
(
namesRoute:
true
,
label:
label
,
child:
dialogChild
);
return
new
Dialog
(
child:
dialogChild
);
}
}
}
}
...
@@ -402,6 +433,7 @@ class SimpleDialog extends StatelessWidget {
...
@@ -402,6 +433,7 @@ class SimpleDialog extends StatelessWidget {
this
.
titlePadding
:
const
EdgeInsets
.
fromLTRB
(
24.0
,
24.0
,
24.0
,
0.0
),
this
.
titlePadding
:
const
EdgeInsets
.
fromLTRB
(
24.0
,
24.0
,
24.0
,
0.0
),
this
.
children
,
this
.
children
,
this
.
contentPadding
:
const
EdgeInsets
.
fromLTRB
(
0.0
,
12.0
,
0.0
,
16.0
),
this
.
contentPadding
:
const
EdgeInsets
.
fromLTRB
(
0.0
,
12.0
,
0.0
,
16.0
),
this
.
semanticLabel
,
})
:
assert
(
titlePadding
!=
null
),
})
:
assert
(
titlePadding
!=
null
),
assert
(
contentPadding
!=
null
),
assert
(
contentPadding
!=
null
),
super
(
key:
key
);
super
(
key:
key
);
...
@@ -443,18 +475,41 @@ class SimpleDialog extends StatelessWidget {
...
@@ -443,18 +475,41 @@ class SimpleDialog extends StatelessWidget {
/// the top padding ends up being 24 pixels.
/// the top padding ends up being 24 pixels.
final
EdgeInsetsGeometry
contentPadding
;
final
EdgeInsetsGeometry
contentPadding
;
/// The semantic label of the dialog used by accessibility frameworks to
/// announce screen transitions when the dialog is opened and closed.
///
/// If this label is not provided, a semantic label will be infered from the
/// [title] if it is not null. If there is no title, the label will be taken
/// from [MaterialLocalizations.dialogLabel].
///
/// See also:
///
/// * [SemanticsConfiguration.isRouteName], for a description of how this
/// value is used.
final
String
semanticLabel
;
@override
@override
Widget
build
(
BuildContext
context
)
{
Widget
build
(
BuildContext
context
)
{
final
List
<
Widget
>
body
=
<
Widget
>[];
final
List
<
Widget
>
body
=
<
Widget
>[];
String
label
=
semanticLabel
;
if
(
title
!=
null
)
{
if
(
title
!=
null
)
{
body
.
add
(
new
Padding
(
body
.
add
(
new
Padding
(
padding:
titlePadding
,
padding:
titlePadding
,
child:
new
DefaultTextStyle
(
child:
new
DefaultTextStyle
(
style:
Theme
.
of
(
context
).
textTheme
.
title
,
style:
Theme
.
of
(
context
).
textTheme
.
title
,
child:
title
,
child:
new
Semantics
(
namesRoute:
true
,
child:
title
)
,
)
)
));
));
}
else
{
switch
(
defaultTargetPlatform
)
{
case
TargetPlatform
.
iOS
:
label
=
semanticLabel
;
break
;
case
TargetPlatform
.
android
:
case
TargetPlatform
.
fuchsia
:
label
=
semanticLabel
??
MaterialLocalizations
.
of
(
context
)?.
dialogLabel
;
}
}
}
if
(
children
!=
null
)
{
if
(
children
!=
null
)
{
...
@@ -466,19 +521,25 @@ class SimpleDialog extends StatelessWidget {
...
@@ -466,19 +521,25 @@ class SimpleDialog extends StatelessWidget {
));
));
}
}
return
new
Dialog
(
Widget
dialogChild
=
new
IntrinsicWidth
(
child:
new
IntrinsicWidth
(
stepWidth:
56.0
,
stepWidth:
56.0
,
child:
new
ConstrainedBox
(
child:
new
ConstrainedBox
(
constraints:
const
BoxConstraints
(
minWidth:
280.0
),
constraints:
const
BoxConstraints
(
minWidth:
280.0
),
child:
new
Column
(
child:
new
Column
(
mainAxisSize:
MainAxisSize
.
min
,
mainAxisSize:
MainAxisSize
.
min
,
crossAxisAlignment:
CrossAxisAlignment
.
stretch
,
crossAxisAlignment:
CrossAxisAlignment
.
stretch
,
children:
body
,
children:
body
,
),
)
),
)
)
);
);
if
(
label
!=
null
)
dialogChild
=
new
Semantics
(
namesRoute:
true
,
label:
label
,
child:
dialogChild
,
);
return
new
Dialog
(
child:
dialogChild
);
}
}
}
}
...
@@ -514,7 +575,14 @@ class _DialogRoute<T> extends PopupRoute<T> {
...
@@ -514,7 +575,14 @@ class _DialogRoute<T> extends PopupRoute<T> {
return
new
SafeArea
(
return
new
SafeArea
(
child:
new
Builder
(
child:
new
Builder
(
builder:
(
BuildContext
context
)
{
builder:
(
BuildContext
context
)
{
return
theme
!=
null
?
new
Theme
(
data:
theme
,
child:
child
)
:
child
;
final
Widget
annotatedChild
=
new
Semantics
(
child:
child
,
scopesRoute:
true
,
explicitChildNodes:
true
,
);
return
theme
!=
null
?
new
Theme
(
data:
theme
,
child:
annotatedChild
)
:
annotatedChild
;
}
}
),
),
);
);
...
@@ -570,9 +638,9 @@ Future<T> showDialog<T>({
...
@@ -570,9 +638,9 @@ Future<T> showDialog<T>({
)
Widget
child
,
)
Widget
child
,
WidgetBuilder
builder
,
WidgetBuilder
builder
,
})
{
})
{
assert
(
child
==
null
||
builder
==
null
);
// ignore: deprecated_member_use
assert
(
child
==
null
||
builder
==
null
);
return
Navigator
.
of
(
context
,
rootNavigator:
true
).
push
(
new
_DialogRoute
<
T
>(
return
Navigator
.
of
(
context
,
rootNavigator:
true
).
push
(
new
_DialogRoute
<
T
>(
child:
child
??
new
Builder
(
builder:
builder
),
// ignore: deprecated_member_use
child:
child
??
new
Builder
(
builder:
builder
),
theme:
Theme
.
of
(
context
,
shadowThemeOnly:
true
),
theme:
Theme
.
of
(
context
,
shadowThemeOnly:
true
),
barrierDismissible:
barrierDismissible
,
barrierDismissible:
barrierDismissible
,
barrierLabel:
MaterialLocalizations
.
of
(
context
).
modalBarrierDismissLabel
,
barrierLabel:
MaterialLocalizations
.
of
(
context
).
modalBarrierDismissLabel
,
...
...
packages/flutter/lib/src/material/drawer.dart
View file @
034a663d
...
@@ -8,6 +8,7 @@ import 'package:flutter/widgets.dart';
...
@@ -8,6 +8,7 @@ import 'package:flutter/widgets.dart';
import
'colors.dart'
;
import
'colors.dart'
;
import
'list_tile.dart'
;
import
'list_tile.dart'
;
import
'material.dart'
;
import
'material.dart'
;
import
'material_localizations.dart'
;
/// The possible alignments of a [Drawer].
/// The possible alignments of a [Drawer].
enum
DrawerAlignment
{
enum
DrawerAlignment
{
...
@@ -85,6 +86,7 @@ class Drawer extends StatelessWidget {
...
@@ -85,6 +86,7 @@ class Drawer extends StatelessWidget {
Key
key
,
Key
key
,
this
.
elevation
:
16.0
,
this
.
elevation
:
16.0
,
this
.
child
,
this
.
child
,
this
.
semanticLabel
,
})
:
super
(
key:
key
);
})
:
super
(
key:
key
);
/// The z-coordinate at which to place this drawer. This controls the size of
/// The z-coordinate at which to place this drawer. This controls the size of
...
@@ -100,13 +102,40 @@ class Drawer extends StatelessWidget {
...
@@ -100,13 +102,40 @@ class Drawer extends StatelessWidget {
/// {@macro flutter.widgets.child}
/// {@macro flutter.widgets.child}
final
Widget
child
;
final
Widget
child
;
/// The semantic label of the dialog used by accessibility frameworks to
/// announce screen transitions when the drawer is opened and closed.
///
/// If this label is not provided, it will default to
/// [MaterialLocalizations.drawerLabel].
///
/// See also:
///
/// * [SemanticsConfiguration.namesRoute], for a description of how this
/// value is used.
final
String
semanticLabel
;
@override
@override
Widget
build
(
BuildContext
context
)
{
Widget
build
(
BuildContext
context
)
{
return
new
ConstrainedBox
(
String
label
=
semanticLabel
;
constraints:
const
BoxConstraints
.
expand
(
width:
_kWidth
),
switch
(
defaultTargetPlatform
)
{
child:
new
Material
(
case
TargetPlatform
.
iOS
:
elevation:
elevation
,
label
=
semanticLabel
;
child:
child
,
break
;
case
TargetPlatform
.
android
:
case
TargetPlatform
.
fuchsia
:
label
=
semanticLabel
??
MaterialLocalizations
.
of
(
context
)?.
drawerLabel
;
}
return
new
Semantics
(
scopesRoute:
true
,
namesRoute:
true
,
explicitChildNodes:
true
,
label:
label
,
child:
new
ConstrainedBox
(
constraints:
const
BoxConstraints
.
expand
(
width:
_kWidth
),
child:
new
Material
(
elevation:
elevation
,
child:
child
,
),
),
),
);
);
}
}
...
...
packages/flutter/lib/src/material/flexible_space_bar.dart
View file @
034a663d
...
@@ -141,6 +141,19 @@ class _FlexibleSpaceBarState extends State<FlexibleSpaceBar> {
...
@@ -141,6 +141,19 @@ class _FlexibleSpaceBarState extends State<FlexibleSpaceBar> {
}
}
if
(
widget
.
title
!=
null
)
{
if
(
widget
.
title
!=
null
)
{
Widget
title
;
switch
(
defaultTargetPlatform
)
{
case
TargetPlatform
.
iOS
:
title
=
widget
.
title
;
break
;
case
TargetPlatform
.
fuchsia
:
case
TargetPlatform
.
android
:
title
=
new
Semantics
(
namesRoute:
true
,
child:
widget
.
title
,
);
}
final
ThemeData
theme
=
Theme
.
of
(
context
);
final
ThemeData
theme
=
Theme
.
of
(
context
);
final
double
opacity
=
settings
.
toolbarOpacity
;
final
double
opacity
=
settings
.
toolbarOpacity
;
if
(
opacity
>
0.0
)
{
if
(
opacity
>
0.0
)
{
...
@@ -163,7 +176,10 @@ class _FlexibleSpaceBarState extends State<FlexibleSpaceBar> {
...
@@ -163,7 +176,10 @@ class _FlexibleSpaceBarState extends State<FlexibleSpaceBar> {
transform:
scaleTransform
,
transform:
scaleTransform
,
child:
new
Align
(
child:
new
Align
(
alignment:
titleAlignment
,
alignment:
titleAlignment
,
child:
new
DefaultTextStyle
(
style:
titleStyle
,
child:
widget
.
title
)
child:
new
DefaultTextStyle
(
style:
titleStyle
,
child:
title
,
)
)
)
)
)
));
));
...
...
packages/flutter/lib/src/material/page.dart
View file @
034a663d
...
@@ -57,7 +57,7 @@ class _MountainViewPageTransition extends StatelessWidget {
...
@@ -57,7 +57,7 @@ class _MountainViewPageTransition extends StatelessWidget {
/// The transition is adaptive to the platform and on iOS, the page slides in
/// The transition is adaptive to the platform and on iOS, the page slides in
/// from the right and exits in reverse. The page also shifts to the left in
/// from the right and exits in reverse. The page also shifts to the left in
/// parallax when another page enters to cover it. (These directions are flipped
/// parallax when another page enters to cover it. (These directions are flipped
/// in environ
e
ments with a right-to-left reading direction.)
/// in environments with a right-to-left reading direction.)
///
///
/// By default, when a modal route is replaced by another, the previous route
/// By default, when a modal route is replaced by another, the previous route
/// remains in memory. To free all the resources when this is not necessary, set
/// remains in memory. To free all the resources when this is not necessary, set
...
@@ -151,7 +151,11 @@ class MaterialPageRoute<T> extends PageRoute<T> {
...
@@ -151,7 +151,11 @@ class MaterialPageRoute<T> extends PageRoute<T> {
@override
@override
Widget
buildPage
(
BuildContext
context
,
Animation
<
double
>
animation
,
Animation
<
double
>
secondaryAnimation
)
{
Widget
buildPage
(
BuildContext
context
,
Animation
<
double
>
animation
,
Animation
<
double
>
secondaryAnimation
)
{
final
Widget
result
=
builder
(
context
);
final
Widget
result
=
new
Semantics
(
scopesRoute:
true
,
explicitChildNodes:
true
,
child:
builder
(
context
),
);
assert
(()
{
assert
(()
{
if
(
result
==
null
)
{
if
(
result
==
null
)
{
throw
new
FlutterError
(
throw
new
FlutterError
(
...
...
packages/flutter/lib/src/material/popup_menu.dart
View file @
034a663d
...
@@ -417,10 +417,12 @@ class _CheckedPopupMenuItemState<T> extends PopupMenuItemState<T, CheckedPopupMe
...
@@ -417,10 +417,12 @@ class _CheckedPopupMenuItemState<T> extends PopupMenuItemState<T, CheckedPopupMe
class
_PopupMenu
<
T
>
extends
StatelessWidget
{
class
_PopupMenu
<
T
>
extends
StatelessWidget
{
const
_PopupMenu
({
const
_PopupMenu
({
Key
key
,
Key
key
,
this
.
route
this
.
route
,
this
.
semanticLabel
,
})
:
super
(
key:
key
);
})
:
super
(
key:
key
);
final
_PopupMenuRoute
<
T
>
route
;
final
_PopupMenuRoute
<
T
>
route
;
final
String
semanticLabel
;
@override
@override
Widget
build
(
BuildContext
context
)
{
Widget
build
(
BuildContext
context
)
{
...
@@ -479,7 +481,13 @@ class _PopupMenu<T> extends StatelessWidget {
...
@@ -479,7 +481,13 @@ class _PopupMenu<T> extends StatelessWidget {
alignment:
AlignmentDirectional
.
topEnd
,
alignment:
AlignmentDirectional
.
topEnd
,
widthFactor:
width
.
evaluate
(
route
.
animation
),
widthFactor:
width
.
evaluate
(
route
.
animation
),
heightFactor:
height
.
evaluate
(
route
.
animation
),
heightFactor:
height
.
evaluate
(
route
.
animation
),
child:
child
,
child:
new
Semantics
(
scopesRoute:
true
,
namesRoute:
true
,
explicitChildNodes:
true
,
label:
semanticLabel
,
child:
child
,
),
),
),
),
),
);
);
...
@@ -577,6 +585,7 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
...
@@ -577,6 +585,7 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
this
.
elevation
,
this
.
elevation
,
this
.
theme
,
this
.
theme
,
this
.
barrierLabel
,
this
.
barrierLabel
,
this
.
semanticLabel
,
});
});
final
RelativeRect
position
;
final
RelativeRect
position
;
...
@@ -584,6 +593,7 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
...
@@ -584,6 +593,7 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
final
dynamic
initialValue
;
final
dynamic
initialValue
;
final
double
elevation
;
final
double
elevation
;
final
ThemeData
theme
;
final
ThemeData
theme
;
final
String
semanticLabel
;
@override
@override
Animation
<
double
>
createAnimation
()
{
Animation
<
double
>
createAnimation
()
{
...
@@ -620,7 +630,7 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
...
@@ -620,7 +630,7 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
}
}
}
}
Widget
menu
=
new
_PopupMenu
<
T
>(
route:
this
);
Widget
menu
=
new
_PopupMenu
<
T
>(
route:
this
,
semanticLabel:
semanticLabel
);
if
(
theme
!=
null
)
if
(
theme
!=
null
)
menu
=
new
Theme
(
data:
theme
,
child:
menu
);
menu
=
new
Theme
(
data:
theme
,
child:
menu
);
...
@@ -680,7 +690,12 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
...
@@ -680,7 +690,12 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
/// The `context` argument is used to look up the [Navigator] and [Theme] for
/// The `context` argument is used to look up the [Navigator] and [Theme] for
/// the menu. It is only used when the method is called. Its corresponding
/// the menu. It is only used when the method is called. Its corresponding
/// widget can be safely removed from the tree before the popup menu is closed.
/// widget can be safely removed from the tree before the popup menu is closed.
///
///
/// The `semanticLabel` argument is used by accessibility frameworks to
/// announce screen transitions when the menu is opened and closed. If this
/// label is not provided, it will default to
/// [MaterialLocalizations.popupMenuLabel].
///
/// See also:
/// See also:
///
///
/// * [PopupMenuItem], a popup menu entry for a single value.
/// * [PopupMenuItem], a popup menu entry for a single value.
...
@@ -688,20 +703,34 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
...
@@ -688,20 +703,34 @@ class _PopupMenuRoute<T> extends PopupRoute<T> {
/// * [CheckedPopupMenuItem], a popup menu item with a checkmark.
/// * [CheckedPopupMenuItem], a popup menu item with a checkmark.
/// * [PopupMenuButton], which provides an [IconButton] that shows a menu by
/// * [PopupMenuButton], which provides an [IconButton] that shows a menu by
/// calling this method automatically.
/// calling this method automatically.
/// * [SemanticsConfiguration.namesRoute], for a description of edge triggered
/// semantics.
Future
<
T
>
showMenu
<
T
>({
Future
<
T
>
showMenu
<
T
>({
@required
BuildContext
context
,
@required
BuildContext
context
,
RelativeRect
position
,
RelativeRect
position
,
@required
List
<
PopupMenuEntry
<
T
>>
items
,
@required
List
<
PopupMenuEntry
<
T
>>
items
,
T
initialValue
,
T
initialValue
,
double
elevation:
8.0
,
double
elevation:
8.0
,
String
semanticLabel
,
})
{
})
{
assert
(
context
!=
null
);
assert
(
context
!=
null
);
assert
(
items
!=
null
&&
items
.
isNotEmpty
);
assert
(
items
!=
null
&&
items
.
isNotEmpty
);
String
label
=
semanticLabel
;
switch
(
defaultTargetPlatform
)
{
case
TargetPlatform
.
iOS
:
label
=
semanticLabel
;
break
;
case
TargetPlatform
.
android
:
case
TargetPlatform
.
fuchsia
:
label
=
semanticLabel
??
MaterialLocalizations
.
of
(
context
)?.
popupMenuLabel
;
}
return
Navigator
.
push
(
context
,
new
_PopupMenuRoute
<
T
>(
return
Navigator
.
push
(
context
,
new
_PopupMenuRoute
<
T
>(
position:
position
,
position:
position
,
items:
items
,
items:
items
,
initialValue:
initialValue
,
initialValue:
initialValue
,
elevation:
elevation
,
elevation:
elevation
,
semanticLabel:
label
,
theme:
Theme
.
of
(
context
,
shadowThemeOnly:
true
),
theme:
Theme
.
of
(
context
,
shadowThemeOnly:
true
),
barrierLabel:
MaterialLocalizations
.
of
(
context
).
modalBarrierDismissLabel
,
barrierLabel:
MaterialLocalizations
.
of
(
context
).
modalBarrierDismissLabel
,
));
));
...
...
packages/flutter/lib/src/rendering/custom_paint.dart
View file @
034a663d
...
@@ -837,6 +837,12 @@ class RenderCustomPaint extends RenderProxyBox {
...
@@ -837,6 +837,12 @@ class RenderCustomPaint extends RenderProxyBox {
if
(
properties
.
header
!=
null
)
{
if
(
properties
.
header
!=
null
)
{
config
.
isHeader
=
properties
.
header
;
config
.
isHeader
=
properties
.
header
;
}
}
if
(
properties
.
scopesRoute
!=
null
)
{
config
.
scopesRoute
=
properties
.
scopesRoute
;
}
if
(
properties
.
namesRoute
!=
null
)
{
config
.
namesRoute
=
properties
.
namesRoute
;
}
if
(
properties
.
label
!=
null
)
{
if
(
properties
.
label
!=
null
)
{
config
.
label
=
properties
.
label
;
config
.
label
=
properties
.
label
;
}
}
...
...
packages/flutter/lib/src/rendering/proxy_box.dart
View file @
034a663d
...
@@ -3019,6 +3019,8 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
...
@@ -3019,6 +3019,8 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
bool
focused
,
bool
focused
,
bool
inMutuallyExclusiveGroup
,
bool
inMutuallyExclusiveGroup
,
bool
obscured
,
bool
obscured
,
bool
scopesRoute
,
bool
namesRoute
,
String
label
,
String
label
,
String
value
,
String
value
,
String
increasedValue
,
String
increasedValue
,
...
@@ -3054,6 +3056,8 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
...
@@ -3054,6 +3056,8 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
_focused
=
focused
,
_focused
=
focused
,
_inMutuallyExclusiveGroup
=
inMutuallyExclusiveGroup
,
_inMutuallyExclusiveGroup
=
inMutuallyExclusiveGroup
,
_obscured
=
obscured
,
_obscured
=
obscured
,
_scopesRoute
=
scopesRoute
,
_namesRoute
=
namesRoute
,
_label
=
label
,
_label
=
label
,
_value
=
value
,
_value
=
value
,
_increasedValue
=
increasedValue
,
_increasedValue
=
increasedValue
,
...
@@ -3213,6 +3217,26 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
...
@@ -3213,6 +3217,26 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
markNeedsSemanticsUpdate
();
markNeedsSemanticsUpdate
();
}
}
/// If non-null, sets the [SemanticsNode.scopesRoute] semantic to the give value.
bool
get
scopesRoute
=>
_scopesRoute
;
bool
_scopesRoute
;
set
scopesRoute
(
bool
value
)
{
if
(
scopesRoute
==
value
)
return
;
_scopesRoute
=
value
;
markNeedsSemanticsUpdate
();
}
/// If non-null, sets the [SemanticsNode.namesRoute] semantic to the give value.
bool
get
namesRoute
=>
_namesRoute
;
bool
_namesRoute
;
set
namesRoute
(
bool
value
)
{
if
(
_namesRoute
==
value
)
return
;
_namesRoute
=
value
;
markNeedsSemanticsUpdate
();
}
/// If non-null, sets the [SemanticsNode.label] semantic to the given value.
/// If non-null, sets the [SemanticsNode.label] semantic to the given value.
///
///
/// The reading direction is given by [textDirection].
/// The reading direction is given by [textDirection].
...
@@ -3633,6 +3657,8 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
...
@@ -3633,6 +3657,8 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
super
.
describeSemanticsConfiguration
(
config
);
super
.
describeSemanticsConfiguration
(
config
);
config
.
isSemanticBoundary
=
container
;
config
.
isSemanticBoundary
=
container
;
config
.
explicitChildNodes
=
explicitChildNodes
;
config
.
explicitChildNodes
=
explicitChildNodes
;
assert
((
scopesRoute
==
true
&&
explicitChildNodes
==
true
)
||
scopesRoute
!=
true
,
'explicitChildNodes must be set to true if scopes route is true'
);
if
(
enabled
!=
null
)
if
(
enabled
!=
null
)
config
.
isEnabled
=
enabled
;
config
.
isEnabled
=
enabled
;
...
@@ -3662,6 +3688,10 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
...
@@ -3662,6 +3688,10 @@ class RenderSemanticsAnnotations extends RenderProxyBox {
config
.
decreasedValue
=
decreasedValue
;
config
.
decreasedValue
=
decreasedValue
;
if
(
hint
!=
null
)
if
(
hint
!=
null
)
config
.
hint
=
hint
;
config
.
hint
=
hint
;
if
(
scopesRoute
!=
null
)
config
.
scopesRoute
=
scopesRoute
;
if
(
namesRoute
!=
null
)
config
.
namesRoute
=
namesRoute
;
if
(
textDirection
!=
null
)
if
(
textDirection
!=
null
)
config
.
textDirection
=
textDirection
;
config
.
textDirection
=
textDirection
;
if
(
sortKey
!=
null
)
if
(
sortKey
!=
null
)
...
...
packages/flutter/lib/src/semantics/semantics.dart
View file @
034a663d
...
@@ -320,6 +320,8 @@ class SemanticsProperties extends DiagnosticableTree {
...
@@ -320,6 +320,8 @@ class SemanticsProperties extends DiagnosticableTree {
this
.
focused
,
this
.
focused
,
this
.
inMutuallyExclusiveGroup
,
this
.
inMutuallyExclusiveGroup
,
this
.
obscured
,
this
.
obscured
,
this
.
scopesRoute
,
this
.
namesRoute
,
this
.
label
,
this
.
label
,
this
.
value
,
this
.
value
,
this
.
increasedValue
,
this
.
increasedValue
,
...
@@ -407,6 +409,25 @@ class SemanticsProperties extends DiagnosticableTree {
...
@@ -407,6 +409,25 @@ class SemanticsProperties extends DiagnosticableTree {
/// Doing so instructs screen readers to not read out the [value].
/// Doing so instructs screen readers to not read out the [value].
final
bool
obscured
;
final
bool
obscured
;
/// If non-null, whether the node corresponds to the root of a subtree for
/// which a route name should be announced.
///
/// Generally, this is set in combination with [explicitChildNodes], since
/// nodes with this flag are not considered focusable by Android or iOS.
///
/// See also:
///
/// * [SemanticsFlag.scopesRoute] for a description of how the announced
/// value is selected.
final
bool
scopesRoute
;
/// If non-null, whether the node contains the semantic label for a route.
///
/// See also:
///
/// * [SemanticsFlag.namesRoute] for a description of how the name is used.
final
bool
namesRoute
;
/// Provides a textual description of the widget.
/// Provides a textual description of the widget.
///
///
/// If a label is provided, there must either by an ambient [Directionality]
/// If a label is provided, there must either by an ambient [Directionality]
...
@@ -2336,6 +2357,25 @@ class SemanticsConfiguration {
...
@@ -2336,6 +2357,25 @@ class SemanticsConfiguration {
_hasBeenAnnotated
=
true
;
_hasBeenAnnotated
=
true
;
}
}
/// Whether the semantics node is the root of a subtree for which values
/// should be announced.
///
/// See also:
/// * [SemanticsFlag.scopesRoute], for a full description of route scoping.
bool
get
scopesRoute
=>
_hasFlag
(
SemanticsFlag
.
scopesRoute
);
set
scopesRoute
(
bool
value
)
{
_setFlag
(
SemanticsFlag
.
scopesRoute
,
value
);
}
/// Whether the semantics node contains the label of a route.
///
/// See also:
/// * [SemanticsFlag.namesRoute], for a full description of route naming.
bool
get
namesRoute
=>
_hasFlag
(
SemanticsFlag
.
namesRoute
);
set
namesRoute
(
bool
value
)
{
_setFlag
(
SemanticsFlag
.
namesRoute
,
value
);
}
/// The reading direction for the text in [label], [value], [hint],
/// The reading direction for the text in [label], [value], [hint],
/// [increasedValue], and [decreasedValue].
/// [increasedValue], and [decreasedValue].
TextDirection
get
textDirection
=>
_textDirection
;
TextDirection
get
textDirection
=>
_textDirection
;
...
...
packages/flutter/lib/src/widgets/basic.dart
View file @
034a663d
...
@@ -4896,6 +4896,8 @@ class Semantics extends SingleChildRenderObjectWidget {
...
@@ -4896,6 +4896,8 @@ class Semantics extends SingleChildRenderObjectWidget {
bool
focused
,
bool
focused
,
bool
inMutuallyExclusiveGroup
,
bool
inMutuallyExclusiveGroup
,
bool
obscured
,
bool
obscured
,
bool
scopesRoute
,
bool
namesRoute
,
String
label
,
String
label
,
String
value
,
String
value
,
String
increasedValue
,
String
increasedValue
,
...
@@ -4934,6 +4936,8 @@ class Semantics extends SingleChildRenderObjectWidget {
...
@@ -4934,6 +4936,8 @@ class Semantics extends SingleChildRenderObjectWidget {
focused:
focused
,
focused:
focused
,
inMutuallyExclusiveGroup:
inMutuallyExclusiveGroup
,
inMutuallyExclusiveGroup:
inMutuallyExclusiveGroup
,
obscured:
obscured
,
obscured:
obscured
,
scopesRoute:
scopesRoute
,
namesRoute:
namesRoute
,
label:
label
,
label:
label
,
value:
value
,
value:
value
,
increasedValue:
increasedValue
,
increasedValue:
increasedValue
,
...
@@ -4995,6 +4999,10 @@ class Semantics extends SingleChildRenderObjectWidget {
...
@@ -4995,6 +4999,10 @@ class Semantics extends SingleChildRenderObjectWidget {
/// information to the semantic tree is to introduce new explicit
/// information to the semantic tree is to introduce new explicit
/// [SemanticNode]s to the tree.
/// [SemanticNode]s to the tree.
///
///
/// If the semantics properties of this node include
/// [SemanticsProperties.scopesRoute] set to true, then [explicitChildNodes]
/// must be true also.
///
/// This setting is often used in combination with [SemanticsConfiguration.isSemanticBoundary]
/// This setting is often used in combination with [SemanticsConfiguration.isSemanticBoundary]
/// to create semantic boundaries that are either writable or not for children.
/// to create semantic boundaries that are either writable or not for children.
final
bool
explicitChildNodes
;
final
bool
explicitChildNodes
;
...
@@ -5013,6 +5021,8 @@ class Semantics extends SingleChildRenderObjectWidget {
...
@@ -5013,6 +5021,8 @@ class Semantics extends SingleChildRenderObjectWidget {
focused:
properties
.
focused
,
focused:
properties
.
focused
,
inMutuallyExclusiveGroup:
properties
.
inMutuallyExclusiveGroup
,
inMutuallyExclusiveGroup:
properties
.
inMutuallyExclusiveGroup
,
obscured:
properties
.
obscured
,
obscured:
properties
.
obscured
,
scopesRoute:
properties
.
scopesRoute
,
namesRoute:
properties
.
namesRoute
,
label:
properties
.
label
,
label:
properties
.
label
,
value:
properties
.
value
,
value:
properties
.
value
,
increasedValue:
properties
.
increasedValue
,
increasedValue:
properties
.
increasedValue
,
...
@@ -5064,6 +5074,8 @@ class Semantics extends SingleChildRenderObjectWidget {
...
@@ -5064,6 +5074,8 @@ class Semantics extends SingleChildRenderObjectWidget {
..
increasedValue
=
properties
.
increasedValue
..
increasedValue
=
properties
.
increasedValue
..
decreasedValue
=
properties
.
decreasedValue
..
decreasedValue
=
properties
.
decreasedValue
..
hint
=
properties
.
hint
..
hint
=
properties
.
hint
..
scopesRoute
=
properties
.
scopesRoute
..
namesRoute
=
properties
.
namesRoute
..
textDirection
=
_getTextDirection
(
context
)
..
textDirection
=
_getTextDirection
(
context
)
..
sortKey
=
properties
.
sortKey
..
sortKey
=
properties
.
sortKey
..
onTap
=
properties
.
onTap
..
onTap
=
properties
.
onTap
...
...
packages/flutter/test/material/date_picker_test.dart
View file @
034a663d
...
@@ -387,6 +387,9 @@ void _tests() {
...
@@ -387,6 +387,9 @@ void _tests() {
final
SemanticsTester
semantics
=
new
SemanticsTester
(
tester
);
final
SemanticsTester
semantics
=
new
SemanticsTester
(
tester
);
await
preparePicker
(
tester
,
(
Future
<
DateTime
>
date
)
async
{
await
preparePicker
(
tester
,
(
Future
<
DateTime
>
date
)
async
{
final
TestSemantics
expected
=
new
TestSemantics
(
final
TestSemantics
expected
=
new
TestSemantics
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
,
],
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
(
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
...
@@ -616,7 +619,7 @@ void _tests() {
...
@@ -616,7 +619,7 @@ void _tests() {
);
);
expect
(
semantics
,
hasSemantics
(
expect
(
semantics
,
hasSemantics
(
expected
,
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
expected
])
,
ignoreId:
true
,
ignoreId:
true
,
ignoreTransform:
true
,
ignoreTransform:
true
,
ignoreRect:
true
,
ignoreRect:
true
,
...
...
packages/flutter/test/material/dialog_test.dart
View file @
034a663d
...
@@ -2,6 +2,8 @@
...
@@ -2,6 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// found in the LICENSE file.
import
'dart:ui'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:matcher/matcher.dart'
;
import
'package:matcher/matcher.dart'
;
...
@@ -332,4 +334,51 @@ void main() {
...
@@ -332,4 +334,51 @@ void main() {
new
Rect
.
fromLTRB
(
40.0
,
24.0
,
800.0
-
40.0
,
600.0
-
24.0
),
new
Rect
.
fromLTRB
(
40.0
,
24.0
,
800.0
-
40.0
,
600.0
-
24.0
),
);
);
});
});
testWidgets
(
'Dialog widget contains route semantics from title'
,
(
WidgetTester
tester
)
async
{
final
SemanticsTester
semantics
=
new
SemanticsTester
(
tester
);
await
tester
.
pumpWidget
(
new
MaterialApp
(
home:
new
Material
(
child:
new
Builder
(
builder:
(
BuildContext
context
)
{
return
new
Center
(
child:
new
RaisedButton
(
child:
const
Text
(
'X'
),
onPressed:
()
{
showDialog
<
void
>(
context:
context
,
builder:
(
BuildContext
context
)
{
return
const
AlertDialog
(
title:
const
Text
(
'Title'
),
content:
const
Text
(
'Y'
),
actions:
const
<
Widget
>[],
);
},
);
},
),
);
},
),
),
),
);
expect
(
semantics
,
isNot
(
includesNodeWith
(
label:
'Title'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
]
)));
await
tester
.
tap
(
find
.
text
(
'X'
));
await
tester
.
pump
();
// start animation
await
tester
.
pump
(
const
Duration
(
seconds:
1
));
expect
(
semantics
,
includesNodeWith
(
label:
'Title'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
));
semantics
.
dispose
();
});
}
}
packages/flutter/test/material/floating_action_button_test.dart
View file @
034a663d
...
@@ -281,14 +281,21 @@ void main() {
...
@@ -281,14 +281,21 @@ void main() {
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
label:
'Add Photo'
,
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
flags:
<
SemanticsFlag
>[
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isButton
,
SemanticsFlag
.
scopesRoute
,
SemanticsFlag
.
hasEnabledState
,
],
SemanticsFlag
.
isEnabled
,
children:
<
TestSemantics
>[
new
TestSemantics
(
label:
'Add Photo'
,
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isButton
,
SemanticsFlag
.
hasEnabledState
,
SemanticsFlag
.
isEnabled
,
],
),
],
],
),
),
],
],
...
...
packages/flutter/test/material/popup_menu_test.dart
View file @
034a663d
...
@@ -2,11 +2,13 @@
...
@@ -2,11 +2,13 @@
// Use of this source code is governed by a BSD-style license that can be
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// found in the LICENSE file.
import
'dart:ui'
show
window
;
import
'dart:ui'
show
window
,
SemanticsFlag
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
import
'../widgets/semantics_tester.dart'
;
void
main
(
)
{
void
main
(
)
{
testWidgets
(
'Navigator.push works within a PopupMenuButton'
,
(
WidgetTester
tester
)
async
{
testWidgets
(
'Navigator.push works within a PopupMenuButton'
,
(
WidgetTester
tester
)
async
{
final
Key
targetKey
=
new
UniqueKey
();
final
Key
targetKey
=
new
UniqueKey
();
...
@@ -427,6 +429,39 @@ void main() {
...
@@ -427,6 +429,39 @@ void main() {
expect
(
MediaQuery
.
of
(
popupContext
).
padding
,
EdgeInsets
.
zero
);
expect
(
MediaQuery
.
of
(
popupContext
).
padding
,
EdgeInsets
.
zero
);
});
});
testWidgets
(
'PopupMenu includes route semantics'
,
(
WidgetTester
tester
)
async
{
final
SemanticsTester
semantics
=
new
SemanticsTester
(
tester
);
await
tester
.
pumpWidget
(
new
MaterialApp
(
home:
new
Material
(
child:
new
PopupMenuButton
<
int
>(
itemBuilder:
(
BuildContext
context
)
{
return
<
PopupMenuItem
<
int
>>[
const
PopupMenuItem
<
int
>(
value:
2
,
child:
const
Text
(
'2'
)),
const
PopupMenuItem
<
int
>(
value:
3
,
child:
const
Text
(
'3'
)),
];
},
child:
const
SizedBox
(
height:
100.0
,
width:
100.0
,
child:
const
Text
(
'XXX'
),
),
),
),
));
await
tester
.
tap
(
find
.
text
(
'XXX'
));
await
tester
.
pumpAndSettle
();
expect
(
semantics
,
includesNodeWith
(
label:
'Popup menu'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
,
SemanticsFlag
.
scopesRoute
,
],
));
semantics
.
dispose
();
});
}
}
class
TestApp
extends
StatefulWidget
{
class
TestApp
extends
StatefulWidget
{
...
...
packages/flutter/test/material/tooltip_test.dart
View file @
034a663d
import
'dart:ui'
;
// Copyright 2015 The Chromium Authors. All rights reserved.
// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// found in the LICENSE file.
...
@@ -486,12 +488,13 @@ void main() {
...
@@ -486,12 +488,13 @@ void main() {
);
);
final
TestSemantics
expected
=
new
TestSemantics
.
root
(
final
TestSemantics
expected
=
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
id:
1
,
id:
1
,
label:
tooltipText
,
label:
'TIP'
,
),
textDirection:
TextDirection
.
ltr
,
]
),
]
);
);
expect
(
semantics
,
hasSemantics
(
expected
,
ignoreTransform:
true
,
ignoreRect:
true
));
expect
(
semantics
,
hasSemantics
(
expected
,
ignoreTransform:
true
,
ignoreRect:
true
));
...
@@ -619,8 +622,13 @@ void main() {
...
@@ -619,8 +622,13 @@ void main() {
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
label:
'Foo
\n
Bar'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
textDirection:
TextDirection
.
ltr
,
children:
<
TestSemantics
>[
new
TestSemantics
(
label:
'Foo
\n
Bar'
,
textDirection:
TextDirection
.
ltr
,
)
],
),
),
],
],
),
ignoreRect:
true
,
ignoreId:
true
,
ignoreTransform:
true
));
),
ignoreRect:
true
,
ignoreId:
true
,
ignoreTransform:
true
));
...
@@ -646,8 +654,13 @@ void main() {
...
@@ -646,8 +654,13 @@ void main() {
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
label:
'Bar'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
textDirection:
TextDirection
.
ltr
,
children:
<
TestSemantics
>[
new
TestSemantics
(
label:
'Bar'
,
textDirection:
TextDirection
.
ltr
,
)
],
),
),
],
],
),
ignoreRect:
true
,
ignoreId:
true
,
ignoreTransform:
true
));
),
ignoreRect:
true
,
ignoreId:
true
,
ignoreTransform:
true
));
...
...
packages/flutter/test/material/user_accounts_drawer_header_test.dart
View file @
034a663d
...
@@ -335,26 +335,31 @@ void main() {
...
@@ -335,26 +335,31 @@ void main() {
new
TestSemantics
(
new
TestSemantics
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
(
label:
'Signed in
\n
name
\n
email'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
textDirection:
TextDirection
.
ltr
,
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
(
label:
r'B'
,
label:
'Signed in
\n
name
\n
email'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
label:
r'C'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
label:
r'D'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isButton
],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
label:
r'Show accounts'
,
textDirection:
TextDirection
.
ltr
,
textDirection:
TextDirection
.
ltr
,
children:
<
TestSemantics
>[
new
TestSemantics
(
label:
r'B'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
label:
r'C'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
label:
r'D'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isButton
],
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
],
label:
r'Show accounts'
,
textDirection:
TextDirection
.
ltr
,
),
],
),
),
],
],
),
),
...
@@ -382,20 +387,25 @@ void main() {
...
@@ -382,20 +387,25 @@ void main() {
new
TestSemantics
(
new
TestSemantics
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
(
label:
'Signed in'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
textDirection:
TextDirection
.
ltr
,
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
(
label:
r'B'
,
label:
'Signed in'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
label:
r'C'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
label:
r'D'
,
textDirection:
TextDirection
.
ltr
,
textDirection:
TextDirection
.
ltr
,
children:
<
TestSemantics
>[
new
TestSemantics
(
label:
r'B'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
label:
r'C'
,
textDirection:
TextDirection
.
ltr
,
),
new
TestSemantics
(
label:
r'D'
,
textDirection:
TextDirection
.
ltr
,
),
],
),
),
],
],
),
),
...
...
packages/flutter/test/widgets/custom_painter_test.dart
View file @
034a663d
...
@@ -416,15 +416,13 @@ void _defineTests() {
...
@@ -416,15 +416,13 @@ void _defineTests() {
inMutuallyExclusiveGroup:
true
,
inMutuallyExclusiveGroup:
true
,
header:
true
,
header:
true
,
obscured:
true
,
obscured:
true
,
scopesRoute:
true
,
namesRoute:
true
,
),
),
),
),
),
),
));
));
// TODO(jonahwilliams): remove when rolling edge semantic support for framework.
final
List
<
SemanticsFlag
>
flags
=
SemanticsFlag
.
values
.
values
.
where
((
SemanticsFlag
flag
)
=>
flag
!=
SemanticsFlag
.
scopesRoute
&&
flag
!=
SemanticsFlag
.
namesRoute
)
.
toList
();
final
TestSemantics
expectedSemantics
=
new
TestSemantics
.
root
(
final
TestSemantics
expectedSemantics
=
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
...
@@ -433,7 +431,7 @@ void _defineTests() {
...
@@ -433,7 +431,7 @@ void _defineTests() {
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
id:
2
,
id:
2
,
rect:
TestSemantics
.
fullScreen
,
rect:
TestSemantics
.
fullScreen
,
flags:
flags
,
flags:
SemanticsFlag
.
values
.
values
.
toList
()
,
),
),
]
]
),
),
...
...
packages/flutter/test/widgets/drawer_test.dart
View file @
034a663d
...
@@ -2,6 +2,8 @@
...
@@ -2,6 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// found in the LICENSE file.
import
'dart:ui'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter/foundation.dart'
;
import
'package:flutter/foundation.dart'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
...
@@ -284,4 +286,40 @@ void main() {
...
@@ -284,4 +286,40 @@ void main() {
semantics
.
dispose
();
semantics
.
dispose
();
});
});
testWidgets
(
'Drawer contains route semantics flags'
,
(
WidgetTester
tester
)
async
{
final
SemanticsTester
semantics
=
new
SemanticsTester
(
tester
);
final
GlobalKey
<
ScaffoldState
>
scaffoldKey
=
new
GlobalKey
<
ScaffoldState
>();
await
tester
.
pumpWidget
(
new
MaterialApp
(
home:
new
Builder
(
builder:
(
BuildContext
context
)
{
return
new
Scaffold
(
key:
scaffoldKey
,
drawer:
const
Drawer
(),
body:
new
Container
(),
);
},
),
),
);
// Open the drawer.
scaffoldKey
.
currentState
.
openDrawer
();
await
tester
.
pump
();
await
tester
.
pump
(
const
Duration
(
milliseconds:
100
));
expect
(
semantics
,
includesNodeWith
(
label:
'Navigation menu'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
,
SemanticsFlag
.
namesRoute
,
],
));
semantics
.
dispose
();
});
}
}
packages/flutter/test/widgets/editable_text_test.dart
View file @
034a663d
...
@@ -593,12 +593,17 @@ void main() {
...
@@ -593,12 +593,17 @@ void main() {
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
(
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
.
rootChild
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isTextField
,
SemanticsFlag
.
isObscured
],
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
value:
expectedValue
,
children:
<
TestSemantics
>[
textDirection:
TextDirection
.
ltr
,
new
TestSemantics
(
nextNodeId:
-
1
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
isTextField
,
SemanticsFlag
.
isObscured
],
previousNodeId:
-
1
,
value:
expectedValue
,
textDirection:
TextDirection
.
ltr
,
nextNodeId:
-
1
,
previousNodeId:
-
1
,
),
],
),
),
],
],
),
ignoreTransform:
true
,
ignoreRect:
true
,
ignoreId:
true
));
),
ignoreTransform:
true
,
ignoreRect:
true
,
ignoreId:
true
));
...
@@ -713,26 +718,32 @@ void main() {
...
@@ -713,26 +718,32 @@ void main() {
await
tester
.
pump
();
await
tester
.
pump
();
final
SemanticsOwner
owner
=
tester
.
binding
.
pipelineOwner
.
semanticsOwner
;
final
SemanticsOwner
owner
=
tester
.
binding
.
pipelineOwner
.
semanticsOwner
;
const
int
expectedNodeId
=
2
;
const
int
expectedNodeId
=
3
;
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
id:
expectedNodeId
,
id:
1
,
flags:
<
SemanticsFlag
>[
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
SemanticsFlag
.
isTextField
,
children:
<
TestSemantics
>[
SemanticsFlag
.
isFocused
new
TestSemantics
.
rootChild
(
],
id:
expectedNodeId
,
actions:
<
SemanticsAction
>[
flags:
<
SemanticsFlag
>[
SemanticsAction
.
moveCursorBackwardByCharacter
,
SemanticsFlag
.
isTextField
,
SemanticsAction
.
setSelection
,
SemanticsFlag
.
isFocused
SemanticsAction
.
copy
,
],
SemanticsAction
.
cut
,
actions:
<
SemanticsAction
>[
SemanticsAction
.
paste
SemanticsAction
.
moveCursorBackwardByCharacter
,
SemanticsAction
.
setSelection
,
SemanticsAction
.
copy
,
SemanticsAction
.
cut
,
SemanticsAction
.
paste
],
value:
'test'
,
textSelection:
new
TextSelection
.
collapsed
(
offset:
controller
.
text
.
length
),
textDirection:
TextDirection
.
ltr
,
),
],
],
value:
'test'
,
textSelection:
new
TextSelection
.
collapsed
(
offset:
controller
.
text
.
length
),
textDirection:
TextDirection
.
ltr
,
),
),
],
],
),
ignoreRect:
true
,
ignoreTransform:
true
));
),
ignoreRect:
true
,
ignoreTransform:
true
));
...
...
packages/flutter/test/widgets/navigator_test.dart
View file @
034a663d
...
@@ -2,9 +2,13 @@
...
@@ -2,9 +2,13 @@
// Use of this source code is governed by a BSD-style license that can be
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// found in the LICENSE file.
import
'dart:ui'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
import
'semantics_tester.dart'
;
class
FirstWidget
extends
StatelessWidget
{
class
FirstWidget
extends
StatelessWidget
{
@override
@override
Widget
build
(
BuildContext
context
)
{
Widget
build
(
BuildContext
context
)
{
...
@@ -769,4 +773,50 @@ void main() {
...
@@ -769,4 +773,50 @@ void main() {
await
tester
.
pumpAndSettle
(
const
Duration
(
milliseconds:
10
));
await
tester
.
pumpAndSettle
(
const
Duration
(
milliseconds:
10
));
expect
(
log
,
<
String
>[
'building B'
,
'building C'
,
'found C'
,
'building D'
,
'building C'
,
'found C'
]);
expect
(
log
,
<
String
>[
'building B'
,
'building C'
,
'found C'
,
'building D'
,
'building C'
,
'found C'
]);
});
});
testWidgets
(
'route semantics'
,
(
WidgetTester
tester
)
async
{
final
SemanticsTester
semantics
=
new
SemanticsTester
(
tester
);
final
Map
<
String
,
WidgetBuilder
>
routes
=
<
String
,
WidgetBuilder
>{
'/'
:
(
BuildContext
context
)
=>
new
OnTapPage
(
id:
'1'
,
onTap:
()
{
Navigator
.
pushNamed
(
context
,
'/A'
);
}),
'/A'
:
(
BuildContext
context
)
=>
new
OnTapPage
(
id:
'2'
,
onTap:
()
{
Navigator
.
pushNamed
(
context
,
'/B/C'
);
}),
'/B/C'
:
(
BuildContext
context
)
=>
const
OnTapPage
(
id:
'3'
),
};
await
tester
.
pumpWidget
(
new
MaterialApp
(
routes:
routes
));
expect
(
semantics
,
includesNodeWith
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
));
expect
(
semantics
,
includesNodeWith
(
label:
'Page 1'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
));
await
tester
.
tap
(
find
.
text
(
'1'
));
// pushNamed('/A')
await
tester
.
pump
();
await
tester
.
pump
(
const
Duration
(
seconds:
1
));
expect
(
semantics
,
includesNodeWith
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
));
expect
(
semantics
,
includesNodeWith
(
label:
'Page 2'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
));
await
tester
.
tap
(
find
.
text
(
'2'
));
// pushNamed('/B/C')
await
tester
.
pump
();
await
tester
.
pump
(
const
Duration
(
seconds:
1
));
expect
(
semantics
,
includesNodeWith
(
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
));
expect
(
semantics
,
includesNodeWith
(
label:
'Page 3'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
));
semantics
.
dispose
();
});
}
}
packages/flutter/test/widgets/semantics_test.dart
View file @
034a663d
...
@@ -471,17 +471,17 @@ void main() {
...
@@ -471,17 +471,17 @@ void main() {
inMutuallyExclusiveGroup:
true
,
inMutuallyExclusiveGroup:
true
,
header:
true
,
header:
true
,
obscured:
true
,
obscured:
true
,
scopesRoute:
true
,
namesRoute:
true
,
explicitChildNodes:
true
,
)
)
);
);
// TODO(jonahwilliams): remove when adding engine support for edge semantics
final
List
<
SemanticsFlag
>
flags
=
SemanticsFlag
.
values
.
values
.
where
((
SemanticsFlag
flag
)
=>
flag
!=
SemanticsFlag
.
scopesRoute
&&
flag
!=
SemanticsFlag
.
namesRoute
)
.
toList
();
final
TestSemantics
expectedSemantics
=
new
TestSemantics
.
root
(
final
TestSemantics
expectedSemantics
=
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
rect:
TestSemantics
.
fullScreen
,
rect:
TestSemantics
.
fullScreen
,
flags:
flags
,
flags:
SemanticsFlag
.
values
.
values
.
toList
()
,
),
),
],
],
);
);
...
...
packages/flutter/test/widgets/semantics_tester_generateTestSemanticsExpressionForCurrentSemanticsTree_test.dart
View file @
034a663d
...
@@ -106,29 +106,35 @@ void _tests() {
...
@@ -106,29 +106,35 @@ void _tests() {
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
(
id:
1
,
id:
1
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
(
id:
4
,
id:
2
,
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
(
new
TestSemantics
(
id:
2
,
id:
5
,
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
children:
<
TestSemantics
>[
label:
'Plain text'
,
new
TestSemantics
(
textDirection:
TextDirection
.
ltr
,
id:
3
,
nextNodeId:
3
,
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
),
label:
'Plain text'
,
new
TestSemantics
(
textDirection:
TextDirection
.
ltr
,
id:
3
,
nextNodeId:
4
,
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
),
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
hasCheckedState
,
SemanticsFlag
.
isChecked
,
SemanticsFlag
.
isSelected
],
new
TestSemantics
(
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
,
SemanticsAction
.
decrease
],
id:
4
,
label:
'Interactive text'
,
tags:
<
SemanticsTag
>[
const
SemanticsTag
(
'RenderViewport.twoPane'
)],
value:
'test-value'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
hasCheckedState
,
SemanticsFlag
.
isChecked
,
SemanticsFlag
.
isSelected
],
increasedValue:
'test-increasedValue'
,
actions:
<
SemanticsAction
>[
SemanticsAction
.
tap
,
SemanticsAction
.
decrease
],
decreasedValue:
'test-decreasedValue'
,
label:
'Interactive text'
,
hint:
'test-hint'
,
value:
'test-value'
,
textDirection:
TextDirection
.
rtl
,
increasedValue:
'test-increasedValue'
,
previousNodeId:
2
,
decreasedValue:
'test-decreasedValue'
,
hint:
'test-hint'
,
textDirection:
TextDirection
.
rtl
,
previousNodeId:
3
,
),
],
),
),
],
],
),
),
...
...
packages/flutter/test/widgets/simple_semantics_test.dart
View file @
034a663d
...
@@ -2,6 +2,8 @@
...
@@ -2,6 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// found in the LICENSE file.
import
'dart:ui'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/rendering.dart'
;
import
'package:flutter/rendering.dart'
;
import
'package:flutter/widgets.dart'
;
import
'package:flutter/widgets.dart'
;
...
@@ -53,12 +55,19 @@ void main() {
...
@@ -53,12 +55,19 @@ void main() {
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
expect
(
semantics
,
hasSemantics
(
new
TestSemantics
.
root
(
children:
<
TestSemantics
>[
children:
<
TestSemantics
>[
new
TestSemantics
.
rootChild
(
new
TestSemantics
.
rootChild
(
rect:
new
Rect
.
fromLTWH
(
0.0
,
0.0
,
800.0
,
600.0
),
id:
2
,
id:
2
,
label:
'Hello!'
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
scopesRoute
],
textDirection:
TextDirection
.
ltr
,
children:
<
TestSemantics
>[
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
10.0
,
10.0
),
new
TestSemantics
(
transform:
new
Matrix4
.
translationValues
(
395.0
,
295.0
,
0.0
),
id:
3
,
)
label:
'Hello!'
,
textDirection:
TextDirection
.
ltr
,
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
10.0
,
10.0
),
transform:
new
Matrix4
.
translationValues
(
395.0
,
295.0
,
0.0
),
)
],
),
],
],
)));
)));
...
...
packages/flutter/test/widgets/sliver_semantics_test.dart
View file @
034a663d
...
@@ -2,6 +2,8 @@
...
@@ -2,6 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// found in the LICENSE file.
import
'dart:ui'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:flutter/rendering.dart'
;
import
'package:flutter/rendering.dart'
;
import
'package:flutter/widgets.dart'
;
import
'package:flutter/widgets.dart'
;
...
@@ -72,6 +74,7 @@ void main() {
...
@@ -72,6 +74,7 @@ void main() {
),
),
new
TestSemantics
(
new
TestSemantics
(
id:
4
,
id:
4
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
label:
r'Semantics Test with Slivers'
,
label:
r'Semantics Test with Slivers'
,
textDirection:
TextDirection
.
ltr
,
textDirection:
TextDirection
.
ltr
,
nextNodeId:
2
,
nextNodeId:
2
,
...
@@ -126,6 +129,7 @@ void main() {
...
@@ -126,6 +129,7 @@ void main() {
),
),
new
TestSemantics
(
new
TestSemantics
(
id:
4
,
id:
4
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
label:
r'Semantics Test with Slivers'
,
label:
r'Semantics Test with Slivers'
,
textDirection:
TextDirection
.
ltr
,
textDirection:
TextDirection
.
ltr
,
previousNodeId:
5
,
previousNodeId:
5
,
...
@@ -176,6 +180,7 @@ void main() {
...
@@ -176,6 +180,7 @@ void main() {
),
),
new
TestSemantics
(
new
TestSemantics
(
id:
4
,
id:
4
,
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
label:
r'Semantics Test with Slivers'
,
label:
r'Semantics Test with Slivers'
,
textDirection:
TextDirection
.
ltr
,
textDirection:
TextDirection
.
ltr
,
nextNodeId:
2
,
nextNodeId:
2
,
...
@@ -412,6 +417,7 @@ void main() {
...
@@ -412,6 +417,7 @@ void main() {
new
TestSemantics
(
new
TestSemantics
(
id:
22
,
id:
22
,
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
120.0
,
20.0
),
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
120.0
,
20.0
),
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
tags:
<
SemanticsTag
>[
RenderViewport
.
excludeFromScrolling
],
tags:
<
SemanticsTag
>[
RenderViewport
.
excludeFromScrolling
],
label:
'AppBar'
,
label:
'AppBar'
,
previousNodeId:
23
,
previousNodeId:
23
,
...
@@ -502,6 +508,7 @@ void main() {
...
@@ -502,6 +508,7 @@ void main() {
id:
28
,
id:
28
,
previousNodeId:
29
,
previousNodeId:
29
,
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
120.0
,
20.0
),
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
120.0
,
20.0
),
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
tags:
<
SemanticsTag
>[
RenderViewport
.
excludeFromScrolling
],
tags:
<
SemanticsTag
>[
RenderViewport
.
excludeFromScrolling
],
label:
'AppBar'
label:
'AppBar'
),
),
...
@@ -594,6 +601,7 @@ void main() {
...
@@ -594,6 +601,7 @@ void main() {
previousNodeId:
35
,
previousNodeId:
35
,
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
120.0
,
20.0
),
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
120.0
,
20.0
),
transform:
new
Matrix4
.
translation
(
new
Vector3
(
0.0
,
544.0
,
0.0
)),
transform:
new
Matrix4
.
translation
(
new
Vector3
(
0.0
,
544.0
,
0.0
)),
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
tags:
<
SemanticsTag
>[
RenderViewport
.
excludeFromScrolling
],
tags:
<
SemanticsTag
>[
RenderViewport
.
excludeFromScrolling
],
label:
'AppBar'
label:
'AppBar'
),
),
...
@@ -685,6 +693,7 @@ void main() {
...
@@ -685,6 +693,7 @@ void main() {
previousNodeId:
41
,
previousNodeId:
41
,
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
120.0
,
20.0
),
rect:
new
Rect
.
fromLTRB
(
0.0
,
0.0
,
120.0
,
20.0
),
transform:
new
Matrix4
.
translation
(
new
Vector3
(
0.0
,
544.0
,
0.0
)),
transform:
new
Matrix4
.
translation
(
new
Vector3
(
0.0
,
544.0
,
0.0
)),
flags:
<
SemanticsFlag
>[
SemanticsFlag
.
namesRoute
],
tags:
<
SemanticsTag
>[
RenderViewport
.
excludeFromScrolling
],
tags:
<
SemanticsTag
>[
RenderViewport
.
excludeFromScrolling
],
label:
'AppBar'
label:
'AppBar'
),
),
...
...
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