Skip to content
This repository has been archived by the owner on Feb 22, 2023. It is now read-only.

Commit

Permalink
Reland "Adds API in semanticsconfiguration to decide how to merge chi…
Browse files Browse the repository at this point in the history
…… (#116895)

* Reland "Adds API in semanticsconfiguration to decide how to merge child semanticsConfigurations (#110730)"

This reverts commit 7549925.

* makes markNeedsSemanticsUpdate more robust

* address comment
  • Loading branch information
chunhtai committed Dec 16, 2022
1 parent ab47fc3 commit 23a2fa3
Show file tree
Hide file tree
Showing 6 changed files with 945 additions and 70 deletions.
104 changes: 85 additions & 19 deletions packages/flutter/lib/src/material/input_decorator.dart
Original file line number Diff line number Diff line change
Expand Up @@ -1329,6 +1329,35 @@ class _RenderDecoration extends RenderBox with SlottedContainerRenderObjectMixin
return Size.zero;
}

ChildSemanticsConfigurationsResult _childSemanticsConfigurationDelegate(List<SemanticsConfiguration> childConfigs) {
final ChildSemanticsConfigurationsResultBuilder builder = ChildSemanticsConfigurationsResultBuilder();
List<SemanticsConfiguration>? prefixMergeGroup;
List<SemanticsConfiguration>? suffixMergeGroup;
for (final SemanticsConfiguration childConfig in childConfigs) {
if (childConfig.tagsChildrenWith(_InputDecoratorState._kPrefixSemanticsTag)) {
prefixMergeGroup ??= <SemanticsConfiguration>[];
prefixMergeGroup.add(childConfig);
} else if (childConfig.tagsChildrenWith(_InputDecoratorState._kSuffixSemanticsTag)) {
suffixMergeGroup ??= <SemanticsConfiguration>[];
suffixMergeGroup.add(childConfig);
} else {
builder.markAsMergeUp(childConfig);
}
}
if (prefixMergeGroup != null) {
builder.markAsSiblingMergeGroup(prefixMergeGroup);
}
if (suffixMergeGroup != null) {
builder.markAsSiblingMergeGroup(suffixMergeGroup);
}
return builder.build();
}

@override
void describeSemanticsConfiguration(SemanticsConfiguration config) {
config.childConfigurationsDelegate = _childSemanticsConfigurationDelegate;
}

@override
void performLayout() {
final BoxConstraints constraints = this.constraints;
Expand Down Expand Up @@ -1716,12 +1745,16 @@ class _AffixText extends StatelessWidget {
this.text,
this.style,
this.child,
this.semanticsSortKey,
required this.semanticsTag,
});

final bool labelIsFloating;
final String? text;
final TextStyle? style;
final Widget? child;
final SemanticsSortKey? semanticsSortKey;
final SemanticsTag semanticsTag;

@override
Widget build(BuildContext context) {
Expand All @@ -1731,7 +1764,11 @@ class _AffixText extends StatelessWidget {
duration: _kTransitionDuration,
curve: _kTransitionCurve,
opacity: labelIsFloating ? 1.0 : 0.0,
child: child ?? (text == null ? null : Text(text!, style: style)),
child: Semantics(
sortKey: semanticsSortKey,
tagForChildren: semanticsTag,
child: child ?? (text == null ? null : Text(text!, style: style)),
),
),
);
}
Expand Down Expand Up @@ -1903,6 +1940,11 @@ class _InputDecoratorState extends State<InputDecorator> with TickerProviderStat
late final Animation<double> _floatingLabelAnimation;
late final AnimationController _shakingLabelController;
final _InputBorderGap _borderGap = _InputBorderGap();
static const OrdinalSortKey _kPrefixSemanticsSortOrder = OrdinalSortKey(0);
static const OrdinalSortKey _kInputSemanticsSortOrder = OrdinalSortKey(1);
static const OrdinalSortKey _kSuffixSemanticsSortOrder = OrdinalSortKey(2);
static const SemanticsTag _kPrefixSemanticsTag = SemanticsTag('_InputDecoratorState.prefix');
static const SemanticsTag _kSuffixSemanticsTag = SemanticsTag('_InputDecoratorState.suffix');

@override
void initState() {
Expand Down Expand Up @@ -2227,22 +2269,42 @@ class _InputDecoratorState extends State<InputDecorator> with TickerProviderStat
),
);

final Widget? prefix = decoration.prefix == null && decoration.prefixText == null ? null :
_AffixText(
labelIsFloating: widget._labelShouldWithdraw,
text: decoration.prefixText,
style: MaterialStateProperty.resolveAs(decoration.prefixStyle, materialState) ?? hintStyle,
child: decoration.prefix,
);

final Widget? suffix = decoration.suffix == null && decoration.suffixText == null ? null :
_AffixText(
labelIsFloating: widget._labelShouldWithdraw,
text: decoration.suffixText,
style: MaterialStateProperty.resolveAs(decoration.suffixStyle, materialState) ?? hintStyle,
child: decoration.suffix,
final bool hasPrefix = decoration.prefix != null || decoration.prefixText != null;
final bool hasSuffix = decoration.suffix != null || decoration.suffixText != null;

Widget? input = widget.child;
// If at least two out of the three are visible, it needs semantics sort
// order.
final bool needsSemanticsSortOrder = widget._labelShouldWithdraw && (input != null ? (hasPrefix || hasSuffix) : (hasPrefix && hasSuffix));

final Widget? prefix = hasPrefix
? _AffixText(
labelIsFloating: widget._labelShouldWithdraw,
text: decoration.prefixText,
style: MaterialStateProperty.resolveAs(decoration.prefixStyle, materialState) ?? hintStyle,
semanticsSortKey: needsSemanticsSortOrder ? _kPrefixSemanticsSortOrder : null,
semanticsTag: _kPrefixSemanticsTag,
child: decoration.prefix,
)
: null;

final Widget? suffix = hasSuffix
? _AffixText(
labelIsFloating: widget._labelShouldWithdraw,
text: decoration.suffixText,
style: MaterialStateProperty.resolveAs(decoration.suffixStyle, materialState) ?? hintStyle,
semanticsSortKey: needsSemanticsSortOrder ? _kSuffixSemanticsSortOrder : null,
semanticsTag: _kSuffixSemanticsTag,
child: decoration.suffix,
)
: null;

if (input != null && needsSemanticsSortOrder) {
input = Semantics(
sortKey: _kInputSemanticsSortOrder,
child: input,
);

}

final bool decorationIsDense = decoration.isDense ?? false;
final double iconSize = decorationIsDense ? 18.0 : 24.0;
Expand Down Expand Up @@ -2281,7 +2343,9 @@ class _InputDecoratorState extends State<InputDecorator> with TickerProviderStat
color: _getPrefixIconColor(themeData, defaults),
size: iconSize,
),
child: decoration.prefixIcon!,
child: Semantics(
child: decoration.prefixIcon,
),
),
),
),
Expand All @@ -2306,7 +2370,9 @@ class _InputDecoratorState extends State<InputDecorator> with TickerProviderStat
color: _getSuffixIconColor(themeData, defaults),
size: iconSize,
),
child: decoration.suffixIcon!,
child: Semantics(
child: decoration.suffixIcon,
),
),
),
),
Expand Down Expand Up @@ -2383,7 +2449,7 @@ class _InputDecoratorState extends State<InputDecorator> with TickerProviderStat
isDense: decoration.isDense,
visualDensity: themeData.visualDensity,
icon: icon,
input: widget.child,
input: input,
label: label,
hint: hint,
prefix: prefix,
Expand Down
Loading

0 comments on commit 23a2fa3

Please sign in to comment.