FormeRadioGroup<T extends Object> constructor

FormeRadioGroup<T extends Object>({
  1. T? initialValue,
  2. required String name,
  3. bool readOnly = false,
  4. required List<FormeListTileItem<T>> items,
  5. int split = 2,
  6. bool dense = true,
  7. ShapeBorder? shape,
  8. ListTileStyle? style,
  9. Color? selectedColor,
  10. Color? iconColor,
  11. Color? textColor,
  12. EdgeInsetsGeometry? contentPadding,
  13. Color? tileColor,
  14. Color? selectedTileColor,
  15. bool? enableFeedback,
  16. double? horizontalTitleGap,
  17. double? minVerticalPadding,
  18. double? minLeadingWidth,
  19. Color? activeColor,
  20. MaterialStateProperty<Color?>? fillColor,
  21. Color? focusColor,
  22. Color? hoverColor,
  23. MaterialStateProperty<Color?>? overlayColor,
  24. double? splashRadius,
  25. VisualDensity? visualDensity,
  26. MaterialTapTargetSize? materialTapTargetSize,
  27. Axis direction = Axis.horizontal,
  28. WrapAlignment alignment = WrapAlignment.start,
  29. WrapAlignment runAlignment = WrapAlignment.start,
  30. double runSpacing = 0.0,
  31. double spacing = 0.0,
  32. WrapCrossAlignment crossAxisAlignment = WrapCrossAlignment.start,
  33. TextDirection? textDirection,
  34. VerticalDirection verticalDirection = VerticalDirection.down,
  35. Key? key,
  36. int? order,
  37. bool quietlyValidate = false,
  38. Duration? asyncValidatorDebounce,
  39. AutovalidateMode? autovalidateMode,
  40. FormeFieldStatusChanged<T?>? onStatusChanged,
  41. dynamic onInitialed,
  42. FormeFieldSetter<T?>? onSaved,
  43. FormeValidator<T?>? validator,
  44. FormeAsyncValidator<T?>? asyncValidator,
  45. InputDecoration? decoration,
  46. FormeFieldDecorator<T?>? decorator,
  47. bool requestFocusOnUserInteraction = true,
  48. bool registrable = true,
  49. bool enabled = true,
  50. dynamic valueUpdater,
  51. FormeFieldValidationFilter<T?>? validationFilter,
  52. FocusNode? focusNode,
})

Implementation

FormeRadioGroup({
  T? initialValue,
  required String name,
  bool readOnly = false,
  required this.items,
  int split = 2,
  bool dense = true,
  ShapeBorder? shape,
  ListTileStyle? style,
  Color? selectedColor,
  Color? iconColor,
  Color? textColor,
  EdgeInsetsGeometry? contentPadding,
  Color? tileColor,
  Color? selectedTileColor,
  bool? enableFeedback,
  double? horizontalTitleGap,
  double? minVerticalPadding,
  double? minLeadingWidth,
  Color? activeColor,
  MaterialStateProperty<Color?>? fillColor,
  Color? focusColor,
  Color? hoverColor,
  MaterialStateProperty<Color?>? overlayColor,
  double? splashRadius,
  VisualDensity? visualDensity,
  MaterialTapTargetSize? materialTapTargetSize,
  Axis direction = Axis.horizontal,
  WrapAlignment alignment = WrapAlignment.start,
  WrapAlignment runAlignment = WrapAlignment.start,
  double runSpacing = 0.0,
  double spacing = 0.0,
  WrapCrossAlignment crossAxisAlignment = WrapCrossAlignment.start,
  TextDirection? textDirection,
  VerticalDirection verticalDirection = VerticalDirection.down,
  Key? key,
  int? order,
  bool quietlyValidate = false,
  Duration? asyncValidatorDebounce,
  AutovalidateMode? autovalidateMode,
  FormeFieldStatusChanged<T?>? onStatusChanged,
  FormeFieldInitialed<T?>? onInitialed,
  FormeFieldSetter<T?>? onSaved,
  FormeValidator<T?>? validator,
  FormeAsyncValidator<T?>? asyncValidator,
  InputDecoration? decoration,
  FormeFieldDecorator<T?>? decorator,
  bool requestFocusOnUserInteraction = true,
  bool registrable = true,
  bool enabled = true,
  FormeFieldValueUpdater<T?>? valueUpdater,
  FormeFieldValidationFilter<T?>? validationFilter,
  FocusNode? focusNode,
}) : super(
          focusNode: focusNode,
          validationFilter: validationFilter,
          valueUpdater: valueUpdater,
          enabled: enabled,
          registrable: registrable,
          requestFocusOnUserInteraction: requestFocusOnUserInteraction,
          quietlyValidate: quietlyValidate,
          asyncValidatorDebounce: asyncValidatorDebounce,
          autovalidateMode: autovalidateMode,
          onStatusChanged: onStatusChanged,
          onInitialed: onInitialed,
          onSaved: onSaved,
          validator: validator,
          asyncValidator: asyncValidator,
          order: order,
          decorator: decorator ??
              (decoration == null
                  ? null
                  : FormeInputDecoratorBuilder(decoration: decoration)),
          key: key,
          readOnly: readOnly,
          name: name,
          initialValue: initialValue,
          builder: (state) {
            final bool readOnly = state.readOnly;
            final List<Widget> wrapWidgets = [];

            void changeValue(T value) {
              state.didChange(value);
              state.requestFocusOnUserInteraction();
            }

            Widget createFormeListTileItem(
                FormeListTileItem<T> item, bool selected, bool readOnly) {
              return RadioListTile<T>(
                shape: shape,
                tileColor: tileColor,
                selectedTileColor: selectedTileColor,
                activeColor: activeColor,
                secondary: item.secondary,
                subtitle: item.subtitle,
                groupValue: state.value,
                controlAffinity: item.controlAffinity,
                contentPadding: item.padding,
                dense: item.dense,
                title: item.title,
                value: item.data,
                onChanged: readOnly ? null : (v) => changeValue(item.data),
              );
            }

            Widget createCommonItem(
                FormeListTileItem<T> item, bool selected, bool readOnly) {
              return Radio<T>(
                activeColor: activeColor,
                fillColor: fillColor,
                materialTapTargetSize: materialTapTargetSize,
                focusColor: focusColor,
                hoverColor: hoverColor,
                overlayColor: overlayColor,
                splashRadius: splashRadius,
                visualDensity: visualDensity,
                value: item.data,
                groupValue: state.value,
                onChanged: readOnly || item.readOnly
                    ? null
                    : (v) => changeValue(item.data),
              );
            }

            for (int i = 0; i < items.length; i++) {
              final FormeListTileItem<T> item = items[i];
              final bool isReadOnly = readOnly || item.readOnly;
              final bool selected = state.value == item.data;
              if (split > 0) {
                final double factor = 1 / split;
                if (factor == 1) {
                  wrapWidgets.add(
                      createFormeListTileItem(item, selected, isReadOnly));
                  continue;
                }
              }

              final Widget tileItem =
                  createCommonItem(item, selected, readOnly);

              final Widget title = split == 0
                  ? item.title
                  : Flexible(
                      child: item.title,
                    );

              List<Widget> children;
              switch (item.controlAffinity) {
                case ListTileControlAffinity.leading:
                  children = [tileItem, title];
                  break;
                default:
                  children = [title, tileItem];
                  break;
              }

              final Row tileItemRow = Row(
                mainAxisSize: MainAxisSize.min,
                children: children,
              );

              final Widget groupItemWidget = Padding(
                padding: item.padding,
                child: InkWell(
                    borderRadius:
                        const BorderRadius.all(Radius.circular(4.0)),
                    onTap: isReadOnly
                        ? null
                        : () {
                            changeValue(item.data);
                          },
                    child: tileItemRow),
              );

              final bool visible = item.visible;
              if (split <= 0) {
                wrapWidgets.add(Visibility(
                  visible: visible,
                  child: groupItemWidget,
                ));
                if (visible && i < items.length - 1) {
                  wrapWidgets.add(const SizedBox(
                    width: 8.0,
                  ));
                }
              } else {
                final double factor = item.ignoreSplit ? 1 : 1 / split;
                wrapWidgets.add(Visibility(
                  visible: visible,
                  child: FractionallySizedBox(
                    widthFactor: factor,
                    child: groupItemWidget,
                  ),
                ));
              }
            }

            Widget child = Wrap(
              spacing: spacing,
              runSpacing: runSpacing,
              textDirection: textDirection,
              crossAxisAlignment: crossAxisAlignment,
              verticalDirection: verticalDirection,
              alignment: alignment,
              direction: direction,
              runAlignment: runAlignment,
              children: wrapWidgets,
            );
            if (split == 1) {
              child = ListTileTheme.merge(
                child: child,
                dense: dense,
                shape: shape,
                style: style,
                selectedColor: selectedColor,
                iconColor: iconColor,
                textColor: textColor,
                contentPadding: contentPadding,
                tileColor: tileColor,
                selectedTileColor: selectedTileColor,
                enableFeedback: enableFeedback,
                horizontalTitleGap: horizontalTitleGap,
                minVerticalPadding: minVerticalPadding,
                minLeadingWidth: minLeadingWidth,
              );
            }

            return Focus(
              focusNode: state.focusNode,
              child: child,
            );
          });