From 179fd0b802d82922e43b9c43c443f8b3504ec902 Mon Sep 17 00:00:00 2001 From: X Code Date: Mon, 31 Jan 2022 00:06:13 -0800 Subject: [PATCH] Fix checkbox not toggled correctly in toolbar button --- lib/src/widgets/controller.dart | 3 +++ lib/src/widgets/raw_editor.dart | 17 +++++++++++++++-- .../toolbar/select_header_style_button.dart | 19 +++++++++++++------ .../toolbar/toggle_check_list_button.dart | 9 ++++++++- 4 files changed, 39 insertions(+), 9 deletions(-) diff --git a/lib/src/widgets/controller.dart b/lib/src/widgets/controller.dart index e06847bd..9c32c05d 100644 --- a/lib/src/widgets/controller.dart +++ b/lib/src/widgets/controller.dart @@ -326,4 +326,7 @@ class QuillController extends ChangeNotifier { baseOffset: math.min(selection.baseOffset, end), extentOffset: math.min(selection.extentOffset, end)); } + + // To notify toolbar buttons directly with attributes + Map toolbarButtonToggler = {}; } diff --git a/lib/src/widgets/raw_editor.dart b/lib/src/widgets/raw_editor.dart index e7f7ff5c..8e2ffead 100644 --- a/lib/src/widgets/raw_editor.dart +++ b/lib/src/widgets/raw_editor.dart @@ -405,8 +405,21 @@ class RawEditorState extends EditorState void _handleCheckboxTap(int offset, bool value) { if (!widget.readOnly) { _disableScrollControllerAnimateOnce = true; - widget.controller.formatText( - offset, 0, value ? Attribute.checked : Attribute.unchecked); + final attribute = value ? Attribute.checked : Attribute.unchecked; + widget.controller.formatText(offset, 0, attribute); + + // Checkbox tapping causes controller.selection to go to offset 0 + // Stop toggling those two toolbar buttons + widget.controller.toolbarButtonToggler = { + Attribute.list.key: attribute, + Attribute.header.key: Attribute.header + }; + + // Go back from offset 0 to current selection + SchedulerBinding.instance!.addPostFrameCallback((_) { + widget.controller.updateSelection( + TextSelection.collapsed(offset: offset), ChangeSource.LOCAL); + }); } } diff --git a/lib/src/widgets/toolbar/select_header_style_button.dart b/lib/src/widgets/toolbar/select_header_style_button.dart index 32d7e7c0..4b482cea 100644 --- a/lib/src/widgets/toolbar/select_header_style_button.dart +++ b/lib/src/widgets/toolbar/select_header_style_button.dart @@ -34,8 +34,7 @@ class _SelectHeaderStyleButtonState extends State { void initState() { super.initState(); setState(() { - _value = - _selectionStyle.attributes[Attribute.header.key] ?? Attribute.header; + _value = _getHeaderValue(); }); widget.controller.addListener(_didChangeEditingValue); } @@ -107,19 +106,27 @@ class _SelectHeaderStyleButtonState extends State { void _didChangeEditingValue() { setState(() { - _value = - _selectionStyle.attributes[Attribute.header.key] ?? Attribute.header; + _value = _getHeaderValue(); }); } + Attribute _getHeaderValue() { + final attr = widget.controller.toolbarButtonToggler[Attribute.header.key]; + if (attr != null) { + // checkbox tapping causes controller.selection to go to offset 0 + widget.controller.toolbarButtonToggler.remove(Attribute.header.key); + return attr; + } + return _selectionStyle.attributes[Attribute.header.key] ?? Attribute.header; + } + @override void didUpdateWidget(covariant SelectHeaderStyleButton oldWidget) { super.didUpdateWidget(oldWidget); if (oldWidget.controller != widget.controller) { oldWidget.controller.removeListener(_didChangeEditingValue); widget.controller.addListener(_didChangeEditingValue); - _value = - _selectionStyle.attributes[Attribute.header.key] ?? Attribute.header; + _value = _getHeaderValue(); } } diff --git a/lib/src/widgets/toolbar/toggle_check_list_button.dart b/lib/src/widgets/toolbar/toggle_check_list_button.dart index cf52ff00..a37296f4 100644 --- a/lib/src/widgets/toolbar/toggle_check_list_button.dart +++ b/lib/src/widgets/toolbar/toggle_check_list_button.dart @@ -55,7 +55,14 @@ class _ToggleCheckListButtonState extends State { } bool _getIsToggled(Map attrs) { - final attribute = attrs[Attribute.list.key]; + var attribute = widget.controller.toolbarButtonToggler[Attribute.list.key]; + + if (attribute == null) { + attribute = attrs[Attribute.list.key]; + } else { + // checkbox tapping causes controller.selection to go to offset 0 + widget.controller.toolbarButtonToggler.remove(Attribute.list.key); + } if (attribute == null) { return false;