tdf#142978 Add a11y check sidebar
Change-Id: I6d9d6dca0118567f68db11b7c0cce60643211ab2 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/149000 Tested-by: Jenkins Reviewed-by: Samuel Mehrbrodt <samuel.mehrbrodt@allotropia.de>
This commit is contained in:
@@ -81,6 +81,26 @@
|
||||
</prop>
|
||||
</node>
|
||||
|
||||
<node oor:name="A11yCheckDeck" oor:op="replace">
|
||||
<prop oor:name="Title" oor:type="xs:string">
|
||||
<value xml:lang="en-US">Accessibility Check</value>
|
||||
</prop>
|
||||
<prop oor:name="Id" oor:type="xs:string">
|
||||
<value>A11yCheckDeck</value>
|
||||
</prop>
|
||||
<prop oor:name="IconURL" oor:type="xs:string">
|
||||
<value>private:graphicrepository/cmd/lc_adddirect.png</value>
|
||||
</prop>
|
||||
<prop oor:name="ContextList">
|
||||
<value oor:separator=";">
|
||||
WriterVariants, any, visible ;
|
||||
</value>
|
||||
</prop>
|
||||
<prop oor:name="OrderIndex" oor:type="xs:int">
|
||||
<value>900</value>
|
||||
</prop>
|
||||
</node>
|
||||
|
||||
<node oor:name="ShapesDeck" oor:op="replace">
|
||||
<prop oor:name="Title" oor:type="xs:string">
|
||||
<value xml:lang="en-US">Shapes</value>
|
||||
@@ -577,6 +597,38 @@
|
||||
</prop>
|
||||
</node>
|
||||
|
||||
<node oor:name="A11yCheckIssuesPanel" oor:op="replace">
|
||||
<prop oor:name="Title" oor:type="xs:string">
|
||||
<value xml:lang="en-US">Accessibility Issues</value>
|
||||
</prop>
|
||||
<prop oor:name="TitleBarIsOptional" oor:type="xs:boolean">
|
||||
<value>true</value>
|
||||
</prop>
|
||||
<prop oor:name="Id" oor:type="xs:string">
|
||||
<value>A11yCheckIssuesPanel</value>
|
||||
</prop>
|
||||
<prop oor:name="DeckId" oor:type="xs:string">
|
||||
<value>A11yCheckDeck</value>
|
||||
</prop>
|
||||
<prop oor:name="DefaultMenuCommand">
|
||||
<value></value>
|
||||
</prop>
|
||||
<prop oor:name="ContextList">
|
||||
<value oor:separator=";">
|
||||
WriterVariants, any, visible ;
|
||||
</value>
|
||||
</prop>
|
||||
<prop oor:name="ImplementationURL" oor:type="xs:string">
|
||||
<value>private:resource/toolpanel/SwPanelFactory/A11yCheckIssuesPanel</value>
|
||||
</prop>
|
||||
<prop oor:name="OrderIndex" oor:type="xs:int">
|
||||
<value>100</value>
|
||||
</prop>
|
||||
<prop oor:name="WantsAWT" oor:type="xs:boolean">
|
||||
<value>false</value>
|
||||
</prop>
|
||||
</node>
|
||||
|
||||
<node oor:name="AreaPropertyPanel" oor:op="replace">
|
||||
<prop oor:name="Title" oor:type="xs:string">
|
||||
<value xml:lang="en-US">Area</value>
|
||||
|
||||
@@ -29,7 +29,7 @@
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkButton" id="accessibilityCheckEntryGotoButton">
|
||||
<property name="label" translatable="yes" context="accessibilitycheckentry|accessibilityCheckEntryGotoButton">Go to Issue</property>
|
||||
<property name="label" translatable="yes" context="accessibilitycheckentry|accessibilityCheckEntryGotoButton">Go to</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="receives-default">True</property>
|
||||
|
||||
@@ -734,6 +734,7 @@ $(eval $(call gb_Library_add_exception_objects,sw,\
|
||||
sw/source/uibase/sidebar/ThemePanel \
|
||||
sw/source/uibase/sidebar/SwPanelFactory \
|
||||
sw/source/uibase/sidebar/WriterInspectorTextPanel \
|
||||
sw/source/uibase/sidebar/A11yCheckIssuesPanel \
|
||||
sw/source/uibase/table/chartins \
|
||||
sw/source/uibase/table/swtablerep \
|
||||
sw/source/uibase/table/tablemgr \
|
||||
|
||||
@@ -285,6 +285,7 @@ $(eval $(call gb_UIConfig_add_uifiles,modules/swriter,\
|
||||
sw/uiconfig/swriter/ui/pagestylespanel \
|
||||
sw/uiconfig/swriter/ui/pageheaderpanel \
|
||||
sw/uiconfig/swriter/ui/pagefooterpanel \
|
||||
sw/uiconfig/swriter/ui/a11ycheckissuespanel \
|
||||
sw/uiconfig/swriter/ui/poseditbox \
|
||||
sw/uiconfig/swriter/ui/sidebarwrap \
|
||||
sw/uiconfig/swriter/ui/sidebarstylepresets \
|
||||
|
||||
@@ -0,0 +1,129 @@
|
||||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
|
||||
/*
|
||||
* This file is part of the LibreOffice project.
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
#include <sal/config.h>
|
||||
|
||||
#include <AccessibilityCheck.hxx>
|
||||
#include <cmdid.h>
|
||||
#include <doc.hxx>
|
||||
#include <docsh.hxx>
|
||||
#include <ndtxt.hxx>
|
||||
#include <wrtsh.hxx>
|
||||
|
||||
#include <sfx2/AccessibilityIssue.hxx>
|
||||
#include <vcl/svapp.hxx>
|
||||
|
||||
#include "A11yCheckIssuesPanel.hxx"
|
||||
|
||||
#include <com/sun/star/lang/IllegalArgumentException.hpp>
|
||||
|
||||
namespace sw::sidebar
|
||||
{
|
||||
AccessibilityCheckEntry::AccessibilityCheckEntry(
|
||||
weld::Container* pParent, std::shared_ptr<sfx::AccessibilityIssue> const& rAccessibilityIssue)
|
||||
: m_xBuilder(Application::CreateBuilder(pParent, "svx/ui/accessibilitycheckentry.ui"))
|
||||
, m_xContainer(m_xBuilder->weld_container("accessibilityCheckEntryBox"))
|
||||
, m_xLabel(m_xBuilder->weld_label("accessibilityCheckEntryLabel"))
|
||||
, m_xGotoButton(m_xBuilder->weld_button("accessibilityCheckEntryGotoButton"))
|
||||
, m_pAccessibilityIssue(rAccessibilityIssue)
|
||||
{
|
||||
m_xLabel->set_label(m_pAccessibilityIssue->m_aIssueText);
|
||||
// lock in the height as including the button so all rows are the same height
|
||||
m_xContainer->set_size_request(-1, m_xContainer->get_preferred_size().Height());
|
||||
m_xGotoButton->set_visible(m_pAccessibilityIssue->canGotoIssue());
|
||||
m_xGotoButton->connect_clicked(LINK(this, AccessibilityCheckEntry, GotoButtonClicked));
|
||||
}
|
||||
|
||||
IMPL_LINK_NOARG(AccessibilityCheckEntry, GotoButtonClicked, weld::Button&, void)
|
||||
{
|
||||
m_pAccessibilityIssue->gotoIssue();
|
||||
}
|
||||
|
||||
std::unique_ptr<PanelLayout> A11yCheckIssuesPanel::Create(weld::Widget* pParent,
|
||||
SfxBindings* pBindings)
|
||||
{
|
||||
if (pParent == nullptr)
|
||||
throw ::com::sun::star::lang::IllegalArgumentException(
|
||||
"no parent window given to A11yCheckIssuesPanel::Create", nullptr, 0);
|
||||
return std::make_unique<A11yCheckIssuesPanel>(pParent, pBindings);
|
||||
}
|
||||
|
||||
A11yCheckIssuesPanel::A11yCheckIssuesPanel(weld::Widget* pParent, SfxBindings* pBindings)
|
||||
: PanelLayout(pParent, "A11yCheckIssuesPanel", "modules/swriter/ui/a11ycheckissuespanel.ui")
|
||||
, m_xAccessibilityCheckBox(m_xBuilder->weld_box("accessibilityCheckBox"))
|
||||
, m_xScrolledWindow(m_xBuilder->weld_scrolled_window("scrolledwindow"))
|
||||
, maA11yCheckController(FN_STAT_ACCESSIBILITY_CHECK, *pBindings, *this)
|
||||
, mnIssueCount(0)
|
||||
{
|
||||
SwDocShell* pDocSh = dynamic_cast<SwDocShell*>(SfxObjectShell::Current());
|
||||
if (!pDocSh)
|
||||
return;
|
||||
|
||||
mpDoc = pDocSh->GetDoc();
|
||||
|
||||
populateIssues();
|
||||
}
|
||||
|
||||
A11yCheckIssuesPanel::~A11yCheckIssuesPanel() { m_xAccessibilityCheckBox.reset(); }
|
||||
|
||||
void A11yCheckIssuesPanel::populateIssues()
|
||||
{
|
||||
if (!mpDoc)
|
||||
return;
|
||||
sw::AccessibilityCheck aCheck(mpDoc);
|
||||
aCheck.check();
|
||||
m_aIssueCollection = aCheck.getIssueCollection();
|
||||
|
||||
// Remove old issue widgets
|
||||
for (auto const& xEntry : m_aAccessibilityCheckEntries)
|
||||
m_xAccessibilityCheckBox->move(xEntry->get_widget(), nullptr);
|
||||
|
||||
sal_Int32 i = 0;
|
||||
for (std::shared_ptr<sfx::AccessibilityIssue> const& pIssue : m_aIssueCollection.getIssues())
|
||||
{
|
||||
auto xEntry
|
||||
= std::make_unique<AccessibilityCheckEntry>(m_xAccessibilityCheckBox.get(), pIssue);
|
||||
m_xAccessibilityCheckBox->reorder_child(xEntry->get_widget(), i++);
|
||||
m_aAccessibilityCheckEntries.push_back(std::move(xEntry));
|
||||
}
|
||||
|
||||
if (!m_aAccessibilityCheckEntries.empty())
|
||||
{
|
||||
auto nRowHeight
|
||||
= m_aAccessibilityCheckEntries.back()->get_widget()->get_preferred_size().Height();
|
||||
// 6 is the spacing set in the .ui
|
||||
m_xScrolledWindow->vadjustment_set_step_increment(nRowHeight + 6);
|
||||
}
|
||||
}
|
||||
|
||||
void A11yCheckIssuesPanel::NotifyItemUpdate(const sal_uInt16 nSid, const SfxItemState /* eState */,
|
||||
const SfxPoolItem* pState)
|
||||
{
|
||||
if (!m_xAccessibilityCheckBox) //disposed
|
||||
return;
|
||||
|
||||
switch (nSid)
|
||||
{
|
||||
case FN_STAT_ACCESSIBILITY_CHECK:
|
||||
{
|
||||
sal_Int32 nIssueCount = static_cast<const SfxInt32Item*>(pState)->GetValue();
|
||||
if (nIssueCount != mnIssueCount)
|
||||
{
|
||||
mnIssueCount = nIssueCount;
|
||||
populateIssues();
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */
|
||||
@@ -0,0 +1,74 @@
|
||||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
|
||||
/*
|
||||
* This file is part of the LibreOffice project.
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <memory>
|
||||
|
||||
#include <sfx2/AccessibilityIssue.hxx>
|
||||
#include <sfx2/sidebar/ControllerItem.hxx>
|
||||
#include <sfx2/sidebar/PanelLayout.hxx>
|
||||
#include <svl/poolitem.hxx>
|
||||
#include <tools/link.hxx>
|
||||
#include <vcl/weld.hxx>
|
||||
|
||||
#include <doc.hxx>
|
||||
|
||||
namespace sw::sidebar
|
||||
{
|
||||
class AccessibilityCheckEntry final
|
||||
{
|
||||
private:
|
||||
std::unique_ptr<weld::Builder> m_xBuilder;
|
||||
std::unique_ptr<weld::Container> m_xContainer;
|
||||
std::unique_ptr<weld::Label> m_xLabel;
|
||||
std::unique_ptr<weld::Button> m_xGotoButton;
|
||||
|
||||
std::shared_ptr<sfx::AccessibilityIssue> const& m_pAccessibilityIssue;
|
||||
|
||||
public:
|
||||
AccessibilityCheckEntry(weld::Container* pParent,
|
||||
std::shared_ptr<sfx::AccessibilityIssue> const& pAccessibilityIssue);
|
||||
|
||||
weld::Widget* get_widget() const { return m_xContainer.get(); }
|
||||
|
||||
DECL_LINK(GotoButtonClicked, weld::Button&, void);
|
||||
};
|
||||
|
||||
class A11yCheckIssuesPanel : public PanelLayout,
|
||||
public ::sfx2::sidebar::ControllerItem::ItemUpdateReceiverInterface
|
||||
{
|
||||
public:
|
||||
static std::unique_ptr<PanelLayout> Create(weld::Widget* pParent, SfxBindings* pBindings);
|
||||
|
||||
virtual void NotifyItemUpdate(const sal_uInt16 nSId, const SfxItemState eState,
|
||||
const SfxPoolItem* pState) override;
|
||||
|
||||
virtual void GetControlState(const sal_uInt16 /*nSId*/,
|
||||
boost::property_tree::ptree& /*rState*/) override{};
|
||||
|
||||
A11yCheckIssuesPanel(weld::Widget* pParent, SfxBindings* pBindings);
|
||||
virtual ~A11yCheckIssuesPanel() override;
|
||||
|
||||
private:
|
||||
std::vector<std::unique_ptr<AccessibilityCheckEntry>> m_aAccessibilityCheckEntries;
|
||||
std::unique_ptr<weld::Box> m_xAccessibilityCheckBox;
|
||||
std::unique_ptr<weld::ScrolledWindow> m_xScrolledWindow;
|
||||
sfx::AccessibilityIssueCollection m_aIssueCollection;
|
||||
std::function<sfx::AccessibilityIssueCollection()> m_getIssueCollection;
|
||||
void populateIssues();
|
||||
|
||||
SwDoc* mpDoc;
|
||||
::sfx2::sidebar::ControllerItem maA11yCheckController;
|
||||
sal_Int32 mnIssueCount;
|
||||
};
|
||||
|
||||
} //end of namespace sw::sidebar
|
||||
|
||||
/* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */
|
||||
@@ -19,6 +19,7 @@
|
||||
|
||||
#include <com/sun/star/ui/XUIElementFactory.hpp>
|
||||
|
||||
#include "A11yCheckIssuesPanel.hxx"
|
||||
#include "ThemePanel.hxx"
|
||||
#include "StylePresetsPanel.hxx"
|
||||
#include "PageStylesPanel.hxx"
|
||||
@@ -196,6 +197,12 @@ Reference<ui::XUIElement> SAL_CALL SwPanelFactory::createUIElement (
|
||||
xElement = sfx2::sidebar::SidebarPanelBase::Create(
|
||||
rsResourceURL, xFrame, std::move(xPanel), ui::LayoutSize(-1,-1,-1));
|
||||
}
|
||||
else if (rsResourceURL.endsWith("/A11yCheckIssuesPanel"))
|
||||
{
|
||||
std::unique_ptr<PanelLayout> xPanel = sw::sidebar::A11yCheckIssuesPanel::Create(pParent, pBindings);
|
||||
xElement = sfx2::sidebar::SidebarPanelBase::Create(
|
||||
rsResourceURL, xFrame, std::move(xPanel), ui::LayoutSize(-1,-1,-1));
|
||||
}
|
||||
|
||||
return xElement;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,49 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.40.0 -->
|
||||
<interface domain="sw">
|
||||
<requires lib="gtk+" version="3.20"/>
|
||||
<object class="GtkBox" id="A11yCheckIssuesPanel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
<property name="hexpand">True</property>
|
||||
<property name="vexpand">True</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkScrolledWindow" id="scrolledwindow">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="hexpand">True</property>
|
||||
<property name="vexpand">True</property>
|
||||
<property name="shadow-type">in</property>
|
||||
<child>
|
||||
<object class="GtkViewport">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
<property name="hexpand">True</property>
|
||||
<property name="vexpand">True</property>
|
||||
<child>
|
||||
<object class="GtkBox" id="accessibilityCheckBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
<property name="valign">start</property>
|
||||
<property name="hexpand">True</property>
|
||||
<property name="vexpand">True</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<property name="spacing">6</property>
|
||||
<property name="homogeneous">True</property>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
||||
Reference in New Issue
Block a user