From 4bb91df62743d88bfd117286e3fd9dc4a38d836e Mon Sep 17 00:00:00 2001 From: Brett Morgan Date: Sat, 28 May 2022 07:00:08 +1000 Subject: [PATCH] Making ToggleButtonState more obvious (#1286) --- .../lib/basic_text_input_client.dart | 2 +- simplistic_editor/lib/main.dart | 76 +++++++++++++------ ...dart => toggle_buttons_state_manager.dart} | 13 +++- 3 files changed, 62 insertions(+), 29 deletions(-) rename simplistic_editor/lib/{toggle_button_state_manager.dart => toggle_buttons_state_manager.dart} (87%) diff --git a/simplistic_editor/lib/basic_text_input_client.dart b/simplistic_editor/lib/basic_text_input_client.dart index e22bb1f2c..941e082dc 100644 --- a/simplistic_editor/lib/basic_text_input_client.dart +++ b/simplistic_editor/lib/basic_text_input_client.dart @@ -7,7 +7,7 @@ import 'package:flutter/services.dart'; import 'replacements.dart'; import 'text_editing_delta_history_manager.dart'; -import 'toggle_button_state_manager.dart'; +import 'toggle_buttons_state_manager.dart'; /// Signature for the callback that reports when the user changes the selection /// (including the cursor location). diff --git a/simplistic_editor/lib/main.dart b/simplistic_editor/lib/main.dart index 0d8756e75..a5bd7b79a 100644 --- a/simplistic_editor/lib/main.dart +++ b/simplistic_editor/lib/main.dart @@ -4,7 +4,7 @@ import 'package:flutter/services.dart'; import 'basic_text_field.dart'; import 'replacements.dart'; import 'text_editing_delta_history_manager.dart'; -import 'toggle_button_state_manager.dart'; +import 'toggle_buttons_state_manager.dart'; void main() { runApp(const MyApp()); @@ -42,7 +42,7 @@ class _MyHomePageState extends State { text: 'The quick brown fox jumps over the lazy dog.', ); final FocusNode _focusNode = FocusNode(); - final List _isSelected = [false, false, false]; + final Set _isSelected = {}; final List _textEditingDeltaHistory = []; void _updateTextEditingDeltaHistory( @@ -115,43 +115,55 @@ class _MyHomePageState extends State { // at the new selection. final List replacementStyles = _replacementTextEditingController.getReplacementsAtSelection(selection); - final List hasChanged = [false, false, false]; + final Set hasChanged = {}; if (replacementStyles.isEmpty) { - _isSelected.fillRange(0, _isSelected.length, false); + _isSelected.removeAll({ + ToggleButtonsState.bold, + ToggleButtonsState.italic, + ToggleButtonsState.underline + }); } for (final TextStyle style in replacementStyles) { - if (style.fontWeight != null && !hasChanged[0]) { - _isSelected[0] = true; - hasChanged[0] = true; + // See [_updateToggleButtonsStateOnButtonPressed] for how + // Bold, Italic and Underline are encoded into [style] + if (style.fontWeight != null && + !hasChanged.contains(ToggleButtonsState.bold)) { + _isSelected.add(ToggleButtonsState.bold); + hasChanged.add(ToggleButtonsState.bold); } - if (style.fontStyle != null && !hasChanged[1]) { - _isSelected[1] = true; - hasChanged[1] = true; + if (style.fontStyle != null && + !hasChanged.contains(ToggleButtonsState.italic)) { + _isSelected.add(ToggleButtonsState.italic); + hasChanged.add(ToggleButtonsState.italic); } - if (style.decoration != null && !hasChanged[2]) { - _isSelected[2] = true; - hasChanged[2] = true; + if (style.decoration != null && + !hasChanged.contains(ToggleButtonsState.underline)) { + _isSelected.add(ToggleButtonsState.underline); + hasChanged.add(ToggleButtonsState.underline); } } for (final TextStyle style in replacementStyles) { - if (style.fontWeight == null && !hasChanged[0]) { - _isSelected[0] = false; - hasChanged[0] = true; + if (style.fontWeight == null && + !hasChanged.contains(ToggleButtonsState.bold)) { + _isSelected.remove(ToggleButtonsState.bold); + hasChanged.add(ToggleButtonsState.bold); } - if (style.fontStyle == null && !hasChanged[1]) { - _isSelected[1] = false; - hasChanged[1] = true; + if (style.fontStyle == null && + !hasChanged.contains(ToggleButtonsState.italic)) { + _isSelected.remove(ToggleButtonsState.italic); + hasChanged.add(ToggleButtonsState.italic); } - if (style.decoration == null && !hasChanged[2]) { - _isSelected[2] = false; - hasChanged[2] = true; + if (style.decoration == null && + !hasChanged.contains(ToggleButtonsState.underline)) { + _isSelected.remove(ToggleButtonsState.underline); + hasChanged.add(ToggleButtonsState.underline); } } @@ -170,8 +182,15 @@ class _MyHomePageState extends State { end: _replacementTextEditingController.selection.end, ); - _isSelected[index] = !_isSelected[index]; - if (_isSelected[index]) { + final targetToggleButtonState = ToggleButtonsState.values[index]; + + if (_isSelected.contains(targetToggleButtonState)) { + _isSelected.remove(targetToggleButtonState); + } else { + _isSelected.add(targetToggleButtonState); + } + + if (_isSelected.contains(targetToggleButtonState)) { _replacementTextEditingController.applyReplacement( TextEditingInlineSpanReplacement( replacementRange, @@ -304,7 +323,14 @@ class _MyHomePageState extends State { return ToggleButtons( borderRadius: const BorderRadius.all(Radius.circular(4.0)), - isSelected: manager.toggleButtonsState, + isSelected: [ + manager.toggleButtonsState + .contains(ToggleButtonsState.bold), + manager.toggleButtonsState + .contains(ToggleButtonsState.italic), + manager.toggleButtonsState + .contains(ToggleButtonsState.underline), + ], onPressed: (index) => manager .updateToggleButtonsOnButtonPressed(index), children: const [ diff --git a/simplistic_editor/lib/toggle_button_state_manager.dart b/simplistic_editor/lib/toggle_buttons_state_manager.dart similarity index 87% rename from simplistic_editor/lib/toggle_button_state_manager.dart rename to simplistic_editor/lib/toggle_buttons_state_manager.dart index 3e176bc05..769dd5f7f 100644 --- a/simplistic_editor/lib/toggle_button_state_manager.dart +++ b/simplistic_editor/lib/toggle_buttons_state_manager.dart @@ -10,11 +10,18 @@ typedef UpdateToggleButtonsStateOnSelectionChangedCallback = void Function( typedef UpdateToggleButtonsStateOnButtonPressedCallback = void Function( int index); +/// The toggle buttons that can be selected. +enum ToggleButtonsState { + bold, + italic, + underline, +} + class ToggleButtonsStateManager extends InheritedWidget { const ToggleButtonsStateManager({ super.key, required super.child, - required List isToggleButtonsSelected, + required Set isToggleButtonsSelected, required UpdateToggleButtonsStateOnButtonPressedCallback updateToggleButtonsStateOnButtonPressed, required UpdateToggleButtonsStateOnSelectionChangedCallback @@ -32,13 +39,13 @@ class ToggleButtonsStateManager extends InheritedWidget { return result!; } - final List _isToggleButtonsSelected; + final Set _isToggleButtonsSelected; final UpdateToggleButtonsStateOnButtonPressedCallback _updateToggleButtonsStateOnButtonPressed; final UpdateToggleButtonsStateOnSelectionChangedCallback _updateToggleButtonStateOnSelectionChanged; - List get toggleButtonsState => _isToggleButtonsSelected; + Set get toggleButtonsState => _isToggleButtonsSelected; UpdateToggleButtonsStateOnButtonPressedCallback get updateToggleButtonsOnButtonPressed => _updateToggleButtonsStateOnButtonPressed;