Skip to content

Commit

Permalink
fix: Fix button group immutability (#1)
Browse files Browse the repository at this point in the history
* Fix errors

* fix copywith function

* [automated commit] lint format and import sort

---------

Co-authored-by: Osman <AO3856@zebra.com>
Co-authored-by: github-actions <github-actions@github.com>
  • Loading branch information
3 people authored and thelukewalton committed Apr 12, 2024
1 parent 16cfd14 commit 0fdf9da
Showing 1 changed file with 98 additions and 35 deletions.
133 changes: 98 additions & 35 deletions lib/src/components/buttons/button_group.dart
Original file line number Diff line number Diff line change
Expand Up @@ -36,18 +36,21 @@ class ZetaButtonGroup extends StatelessWidget {

/// Returns [ZetaGroupButton]s with there appropriate styling.
List<ZetaGroupButton> getButtons() {
for (final element in buttons) {
element
.._isInitial = element._isFinal = false
.._isLarge = isLarge
.._rounded = rounded
.._isInverse = isInverse;
final List<ZetaGroupButton> mappedButtons = [];

for (final (index, button) in buttons.indexed) {
mappedButtons.add(
button.copyWith(
large: isLarge,
inverse: isInverse,
round: rounded,
fin: index == buttons.length - 1,
initial: index == 0,
),
);
}

buttons.first._isInitial = true;
buttons.last._isFinal = true;

return buttons;
return mappedButtons;
}

@override
Expand All @@ -63,34 +66,59 @@ class ZetaButtonGroup extends StatelessWidget {
// TODO(UX-854): Create country variant.

/// Group Button item
// ignore: must_be_immutable
class ZetaGroupButton extends StatefulWidget {
/// Constructs [ZetaGroupButton]
ZetaGroupButton({

/// Public Constructor for [ZetaGroupButton]
const ZetaGroupButton({
super.key,
this.label,
this.icon,
this.onPressed,
this.dropdown,
}) : isFinal = false,
isInitial = false,
isInverse = false,
isLarge = true,
rounded = true;
/// Private constructor
const ZetaGroupButton._({
super.key,
this.label,
this.icon,
this.onPressed,
this.dropdown,
required this.isFinal,
required this.isInitial,
required this.isInverse,
required this.isLarge,
required this.rounded,
});

/// Constructs dropdown group button
ZetaGroupButton.dropdown({
const ZetaGroupButton.dropdown({
super.key,
required this.onPressed,
required this.dropdown,
this.icon,
this.label,
});
}) : isFinal = false,
isInitial = false,
isInverse = false,
isLarge = true,
rounded = true;

///Constructs group button with icon
ZetaGroupButton.icon({
const ZetaGroupButton.icon({
super.key,
required this.icon,
this.dropdown,
this.onPressed,
this.label,
});
}) : isFinal = false,
isInitial = false,
isInverse = false,
isLarge = true,
rounded = true;

/// Label for [ZetaGroupButton].
final String? label;
Expand All @@ -105,29 +133,43 @@ class ZetaGroupButton extends StatefulWidget {
final Widget? dropdown;

///If [ZetaGroupButton] is large.
bool _isLarge = false;
final bool isLarge;

///If [ZetaGroupButton] is rounded.
bool _rounded = false;
final bool rounded;

/// If [ZetaGroupButton] is the first button in its list.
bool _isInitial = false;
final bool isInitial;

/// If [ZetaGroupButton] is the final button in its list.
bool _isFinal = false;
final bool isFinal;

bool _isInverse = false;
/// If [ZetaGroupButton] is inverse.
final bool isInverse;

@override
State<ZetaGroupButton> createState() => _ZetaGroupButtonState();

/// Returns copy of [ZetaGroupButton] with fields.
ZetaGroupButton copyWith({bool? isFinal, bool? isInitial}) {
return ZetaGroupButton(
ZetaGroupButton copyWith({
bool? fin,
bool? initial,
bool? large,
bool? round,
bool? inverse,
}) {
return ZetaGroupButton._(
key: key,
label: label,
icon: icon,
onPressed: onPressed,
dropdown: dropdown,
isFinal: fin ?? isFinal,
isInitial: initial ?? isInitial,
isLarge: large ?? isLarge,
rounded: round ?? rounded,
isInverse: inverse ?? isInverse,
);
}

Expand All @@ -137,7 +179,12 @@ class ZetaGroupButton extends StatefulWidget {
properties
..add(StringProperty('Label', label))
..add(DiagnosticsProperty<IconData?>('icon', icon))
..add(ObjectFlagProperty<VoidCallback?>.has('onPressed', onPressed));
..add(ObjectFlagProperty<VoidCallback?>.has('onPressed', onPressed))
..add(DiagnosticsProperty<bool>('isInitial', isInitial))
..add(DiagnosticsProperty<bool>('isLarge', isLarge))
..add(DiagnosticsProperty<bool>('rounded', rounded))
..add(DiagnosticsProperty<bool>('isFinal', isFinal))
..add(DiagnosticsProperty<bool>('isInverse', isInverse));
}
}

Expand All @@ -156,11 +203,19 @@ class _ZetaGroupButtonState extends State<ZetaGroupButton> {
});
}

@override
void didUpdateWidget(ZetaGroupButton oldWidget) {
super.didUpdateWidget(oldWidget);
if (oldWidget.onPressed != widget.onPressed) {
setState(() {});
}
}

@override
Widget build(BuildContext context) {
final colors = Zeta.of(context).colors;

final borderType = widget._rounded ? ZetaWidgetBorder.rounded : ZetaWidgetBorder.sharp;
final borderType = widget.rounded ? ZetaWidgetBorder.rounded : ZetaWidgetBorder.sharp;

final BorderSide borderSide = _getBorderSide(controller.value, colors, false);

Expand All @@ -172,7 +227,7 @@ class _ZetaGroupButtonState extends State<ZetaGroupButton> {
bottom: borderSide,
right: controller.value.contains(MaterialState.focused)
? BorderSide(color: colors.blue.shade50, width: 2)
: (widget._isFinal)
: (widget.isFinal)
? borderSide
: BorderSide.none,
),
Expand All @@ -190,15 +245,18 @@ class _ZetaGroupButtonState extends State<ZetaGroupButton> {
if (widget.icon != null) Icon(widget.icon),
Text(widget.label!),
if (widget.dropdown != null) // TODO(UX-1006): Dropdown
Icon(widget._rounded ? ZetaIcons.expand_more_round : ZetaIcons.expand_more_sharp, size: 20),
Icon(
widget.rounded ? ZetaIcons.expand_more_round : ZetaIcons.expand_more_sharp,
size: 20,
),
],
).paddingAll(_padding),
),
),
);
}

double get _padding => widget._isLarge ? ZetaSpacing.x4 : ZetaSpacing.x3;
double get _padding => widget.isLarge ? ZetaSpacing.x4 : ZetaSpacing.x3;

BorderSide _getBorderSide(
Set<MaterialState> states,
Expand All @@ -208,7 +266,7 @@ class _ZetaGroupButtonState extends State<ZetaGroupButton> {
if (states.contains(MaterialState.focused)) {
return BorderSide(color: colors.blue.shade50, width: ZetaSpacing.x0_5);
}
if (widget._isInverse) return BorderSide(color: colors.black);
if (widget.isInverse) return BorderSide(color: colors.black);
if (states.contains(MaterialState.disabled)) {
return BorderSide(color: colors.cool.shade40);
}
Expand All @@ -218,13 +276,13 @@ class _ZetaGroupButtonState extends State<ZetaGroupButton> {
}

BorderRadius _getRadius(ZetaWidgetBorder borderType) {
if (widget._isInitial) {
if (widget.isInitial) {
return borderType.radius.copyWith(
topRight: Radius.zero,
bottomRight: Radius.zero,
);
}
if (widget._isFinal) {
if (widget.isFinal) {
return borderType.radius.copyWith(
topLeft: Radius.zero,
bottomLeft: Radius.zero,
Expand All @@ -241,7 +299,7 @@ class _ZetaGroupButtonState extends State<ZetaGroupButton> {
),
),
backgroundColor: MaterialStateProperty.resolveWith<Color?>((states) {
if (widget._isInverse) return colors.cool.shade100;
if (widget.isInverse) return colors.cool.shade100;

if (states.contains(MaterialState.disabled)) {
return colors.surfaceDisabled;
Expand All @@ -258,7 +316,7 @@ class _ZetaGroupButtonState extends State<ZetaGroupButton> {
if (states.contains(MaterialState.disabled)) {
return colors.textDisabled;
}
if (widget._isInverse) return colors.cool.shade100.onColor;
if (widget.isInverse) return colors.cool.shade100.onColor;
return colors.textDefault;
}),
elevation: const MaterialStatePropertyAll(0),
Expand All @@ -269,6 +327,11 @@ class _ZetaGroupButtonState extends State<ZetaGroupButton> {
@override
void debugFillProperties(DiagnosticPropertiesBuilder properties) {
super.debugFillProperties(properties);
properties.add(DiagnosticsProperty<MaterialStatesController>('controller', controller));
properties.add(
DiagnosticsProperty<MaterialStatesController>(
'controller',
controller,
),
);
}
}

0 comments on commit 0fdf9da

Please sign in to comment.