Skip to content

Commit f1a1f27

Browse files
authored
[M3] Add error state support for side property of CheckBox (#118386)
* Add error state support for side property * lint fixes * lint fixes
1 parent 0d91c03 commit f1a1f27

File tree

2 files changed

+82
-1
lines changed

2 files changed

+82
-1
lines changed

packages/flutter/lib/src/material/checkbox.dart

+3-1
Original file line numberDiff line numberDiff line change
@@ -321,6 +321,7 @@ class Checkbox extends StatefulWidget {
321321
/// * [MaterialState.hovered].
322322
/// * [MaterialState.focused].
323323
/// * [MaterialState.disabled].
324+
/// * [MaterialState.error].
324325
///
325326
/// If this property is not a [MaterialStateBorderSide] and it is
326327
/// non-null, then it is only rendered when the checkbox's value is
@@ -396,7 +397,8 @@ class _CheckboxState extends State<Checkbox> with TickerProviderStateMixin, Togg
396397

397398
BorderSide? _resolveSide(BorderSide? side) {
398399
if (side is MaterialStateBorderSide) {
399-
return MaterialStateProperty.resolveAs<BorderSide?>(side, states);
400+
final Set<MaterialState> sideStates = widget.isError ? (states..add(MaterialState.error)) : states;
401+
return MaterialStateProperty.resolveAs<BorderSide?>(side, sideStates);
400402
}
401403
if (!states.contains(MaterialState.selected)) {
402404
return side;

packages/flutter/test/material/checkbox_test.dart

+79
Original file line numberDiff line numberDiff line change
@@ -1656,6 +1656,85 @@ void main() {
16561656
await gestureLongPress.up();
16571657
await tester.pump();
16581658
});
1659+
1660+
testWidgets('Checkbox MaterialStateBorderSide applies in error states - M3', (WidgetTester tester) async {
1661+
final FocusNode focusNode = FocusNode(debugLabel: 'Checkbox');
1662+
final ThemeData themeData = ThemeData(useMaterial3: true);
1663+
const Color borderColor = Color(0xffffeb3b);
1664+
tester.binding.focusManager.highlightStrategy = FocusHighlightStrategy.alwaysTraditional;
1665+
bool? value = false;
1666+
Widget buildApp({bool autoFocus = true}) {
1667+
return MaterialApp(
1668+
theme: themeData,
1669+
home: Material(
1670+
child: Center(
1671+
child: StatefulBuilder(builder: (BuildContext context, StateSetter setState) {
1672+
return Checkbox(
1673+
isError: true,
1674+
side: MaterialStateBorderSide.resolveWith((Set<MaterialState> states) {
1675+
if (states.contains(MaterialState.error)) {
1676+
return const BorderSide(color: borderColor, width: 4);
1677+
}
1678+
return const BorderSide(color: Colors.red, width: 2);
1679+
}),
1680+
value: value,
1681+
onChanged: (bool? newValue) {
1682+
setState(() {
1683+
value = newValue;
1684+
});
1685+
},
1686+
autofocus: autoFocus,
1687+
focusNode: focusNode,
1688+
);
1689+
}),
1690+
),
1691+
),
1692+
);
1693+
}
1694+
1695+
void expectBorder() {
1696+
expect(
1697+
tester.renderObject<RenderBox>(find.byType(Checkbox)),
1698+
paints
1699+
..drrect(
1700+
color: borderColor,
1701+
outer: RRect.fromLTRBR(15, 15, 33, 33, const Radius.circular(1)),
1702+
inner: RRect.fromLTRBR(19, 19, 29, 29, Radius.zero),
1703+
),
1704+
);
1705+
}
1706+
1707+
await tester.pumpWidget(buildApp());
1708+
await tester.pumpAndSettle();
1709+
expectBorder();
1710+
1711+
// Focused
1712+
await tester.pumpWidget(buildApp());
1713+
await tester.pumpAndSettle();
1714+
expect(focusNode.hasPrimaryFocus, isTrue);
1715+
expectBorder();
1716+
1717+
// Default color
1718+
await tester.pumpWidget(Container());
1719+
await tester.pumpWidget(buildApp(autoFocus: false));
1720+
await tester.pumpAndSettle();
1721+
expect(focusNode.hasPrimaryFocus, isFalse);
1722+
expectBorder();
1723+
1724+
// Start hovering
1725+
final TestGesture gesture = await tester.createGesture(kind: PointerDeviceKind.mouse);
1726+
await gesture.addPointer();
1727+
await gesture.moveTo(tester.getCenter(find.byType(Checkbox)));
1728+
await tester.pumpAndSettle();
1729+
expectBorder();
1730+
1731+
// Start pressing
1732+
final TestGesture gestureLongPress = await tester.startGesture(tester.getCenter(find.byType(Checkbox)));
1733+
await tester.pump();
1734+
expectBorder();
1735+
await gestureLongPress.up();
1736+
await tester.pump();
1737+
});
16591738
}
16601739

16611740
class _SelectedGrabMouseCursor extends MaterialStateMouseCursor {

0 commit comments

Comments
 (0)