summaryrefslogtreecommitdiff
path: root/accessibility
diff options
context:
space:
mode:
authorMichael Weghorn <m.weghorn@posteo.de>2024-05-10 15:35:23 +0200
committerMichael Weghorn <m.weghorn@posteo.de>2024-05-10 21:49:49 +0200
commitab7a94b8403e7fc89398a603a10e9002bd7e2077 (patch)
treeead1345fe7540427ea6c9fc2d6909e1753547f52 /accessibility
parentb1c77f927aced5eeaebd5c17c30efdc1df74c4f9 (diff)
tdf#160971 a11y: Send full text on changed combobox text
When the text of an editable combobox is changed (e.g. using the up/down keys), the Orca screen reader on Linux announces the newly inserted text. This has been the case for other GTK or Qt applications for a while, and with recent Orca commit [1] commit 3a9e6b8d7b16bf2fc7919868cfd1a16e44422710 Author: Michael Weghorn <m.weghorn@posteo.de> Date: Fri May 10 10:16:58 2024 +0200 soffice: Use default logic for editable combobox value change , the same logic is used for LibreOffice as well. For the gtk3 VCL plugin which has a custom combobox implementation using native GTK widgets, this generally works since commit 9f078ed7b625e86182d64d5ccfbb410cdd38081c Author: Michael Weghorn <m.weghorn@posteo.de> Date: Tue May 7 10:04:16 2024 +0200 tdf#160971 gtk3 a11y: Set role for custom editable combobox However, the qt6 VCL plugin uses the VCL combobox implementation, and only the actual difference between the text of the previous and current entry was sent in the TEXT_CHANGED event, resulting in Orca only announcing those letters that were added/changed, e.g. just "ans Narrow" when changing the font in the Writer formatting toolbar from "Liberation Serif" to "Liberation Sans Narrow". This doesn't really make clear what entry is selected. Align the a11y event with what GTK and Qt do and set the full old and new entry texts in the event. To do that, add a new virtual `VCLXAccessibleTextComponent:PreferFullTextInTextChangedEvent` that defaults to false to keep the previous behavior as default, and override it for `VCLXAccessibleEdit` to return true in the case that the edit is the subedit of a combobox (the parent has a combobox role). Use this in `VCLXAccessibleTextComponent::SetText` to determine whether to notify just of the changed characters or to send the whole old/new text. With this in place, Orca also announces the whole new entry text (e.g. "Liberation Sans Narrow" for the above example) when using the qt6 VCL plugin. (It currently additionally announces an extra "Selection deleted" when switching entries, as the text selection also changes, but that aspect is to be handled separate from this change here.) [1] https://gitlab.gnome.org/GNOME/orca/-/commit/3a9e6b8d7b16bf2fc7919868cfd1a16e44422710 Change-Id: I240aa0ad5ac9585e007d67a8c69e305cf1f38185 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/167479 Tested-by: Jenkins Reviewed-by: Michael Weghorn <m.weghorn@posteo.de>
Diffstat (limited to 'accessibility')
-rw-r--r--accessibility/inc/standard/vclxaccessibleedit.hxx3
-rw-r--r--accessibility/inc/standard/vclxaccessibletextcomponent.hxx5
-rw-r--r--accessibility/source/standard/vclxaccessibleedit.cxx16
-rw-r--r--accessibility/source/standard/vclxaccessibletextcomponent.cxx18
4 files changed, 41 insertions, 1 deletions
diff --git a/accessibility/inc/standard/vclxaccessibleedit.hxx b/accessibility/inc/standard/vclxaccessibleedit.hxx
index b3b6a239b9d7..187a03264718 100644
--- a/accessibility/inc/standard/vclxaccessibleedit.hxx
+++ b/accessibility/inc/standard/vclxaccessibleedit.hxx
@@ -50,6 +50,9 @@ protected:
virtual OUString implGetText() override;
virtual void implGetSelection( sal_Int32& nStartIndex, sal_Int32& nEndIndex ) override;
+ // VCLXAccessibleTextComponent
+ virtual bool PreferFullTextInTextChangedEvent() override;
+
public:
VCLXAccessibleEdit( VCLXWindow* pVCLXindow );
diff --git a/accessibility/inc/standard/vclxaccessibletextcomponent.hxx b/accessibility/inc/standard/vclxaccessibletextcomponent.hxx
index 3585dd778574..9678eb15469b 100644
--- a/accessibility/inc/standard/vclxaccessibletextcomponent.hxx
+++ b/accessibility/inc/standard/vclxaccessibletextcomponent.hxx
@@ -40,6 +40,11 @@ class VCLXAccessibleTextComponent : public cppu::ImplInheritanceHelper<
protected:
void SetText( const OUString& sText );
+ // Whether text segments for old/new value in AccessibleEventId::TEXT_CHANGED
+ // event should always include the whole old and new text instead of just
+ // the characters that changed between the two
+ virtual bool PreferFullTextInTextChangedEvent() { return false; };
+
virtual void ProcessWindowEvent( const VclWindowEvent& rVclWindowEvent ) override;
// OCommonAccessibleText
diff --git a/accessibility/source/standard/vclxaccessibleedit.cxx b/accessibility/source/standard/vclxaccessibleedit.cxx
index f29e3224e293..0ab1580f3cca 100644
--- a/accessibility/source/standard/vclxaccessibleedit.cxx
+++ b/accessibility/source/standard/vclxaccessibleedit.cxx
@@ -162,6 +162,22 @@ void VCLXAccessibleEdit::implGetSelection( sal_Int32& nStartIndex, sal_Int32& nE
nEndIndex = aSelection.Max();
}
+// VCLXAccessibleTextComponent
+bool VCLXAccessibleEdit::PreferFullTextInTextChangedEvent()
+{
+ // for a combobox subedit, the Orca screen reader announces the new/added text
+ // so always send the whole old and new text and not just
+ // the changed characters, so the whole entry text gets announced
+ Reference<XAccessible> xParent = getAccessibleParent();
+ if (xParent.is())
+ {
+ Reference<XAccessibleContext> xParentContext = xParent->getAccessibleContext();
+ if (xParentContext.is() && xParentContext->getAccessibleRole() == AccessibleRole::COMBO_BOX)
+ return true;
+ }
+
+ return false;
+}
// XServiceInfo
diff --git a/accessibility/source/standard/vclxaccessibletextcomponent.cxx b/accessibility/source/standard/vclxaccessibletextcomponent.cxx
index f876f0b9ed38..0bf781f09758 100644
--- a/accessibility/source/standard/vclxaccessibletextcomponent.cxx
+++ b/accessibility/source/standard/vclxaccessibletextcomponent.cxx
@@ -56,7 +56,23 @@ VCLXAccessibleTextComponent::VCLXAccessibleTextComponent( VCLXWindow* pVCLXWindo
void VCLXAccessibleTextComponent::SetText( const OUString& sText )
{
Any aOldValue, aNewValue;
- if ( implInitTextChangedEvent( m_sText, sText, aOldValue, aNewValue ) )
+ bool bChanged = false;
+ if (!PreferFullTextInTextChangedEvent())
+ {
+ bChanged = implInitTextChangedEvent(m_sText, sText, aOldValue, aNewValue);
+
+ }
+ else if (sText != m_sText)
+ {
+ // use the full old/new text as old/new value
+ TextSegment aDeletedText(m_sText, 0, m_sText.getLength());
+ aOldValue <<= aDeletedText;
+ TextSegment aInsertedText(sText, 0, sText.getLength());
+ aNewValue <<= aInsertedText;
+ bChanged = true;
+ }
+
+ if (bChanged)
{
m_sText = sText;
NotifyAccessibleEvent( AccessibleEventId::TEXT_CHANGED, aOldValue, aNewValue );