[Libreoffice-commits] help.git: help3xsl/a11y-toggle.js help3xsl/default.css help3xsl/help2.js help3xsl/online_transform.xsl Package_html_static.mk

Libreoffice Gerrit user logerrit at kemper.freedesktop.org
Sat May 18 11:34:48 UTC 2019


 Package_html_static.mk        |    1 
 help3xsl/a11y-toggle.js       |  100 ++++++++++++++++++++++++++++++++++++++++++
 help3xsl/default.css          |   40 +++++++++-------
 help3xsl/help2.js             |   16 ++++--
 help3xsl/online_transform.xsl |   11 ++--
 5 files changed, 142 insertions(+), 26 deletions(-)

New commits:
commit 301ae74e8bab8cded3592588021090ff75f2bf21
Author:     Ilmari Lauhakangas <ilmari.lauhakangas at libreoffice.org>
AuthorDate: Fri May 17 15:10:50 2019 +0300
Commit:     Olivier Hallot <olivier.hallot at libreoffice.org>
CommitDate: Sat May 18 13:34:26 2019 +0200

    Improve accessibility for modules and lang menus
    
    Ever since the contents of the modules and lang menus started
    being populated upon click, the flow for screenreader users has
    been potentially confusing.
    
    This patch introduces a11y-toggle into the mix:
    https://github.com/edenspiekermann/a11y-toggle
    Checkboxes were changed into buttons. This hopefully makes it
    clear we want the user to click them.
    
    The contents tree still uses the checkbox hack, because its items
    are populated upon page load.
    
    Change-Id: I3482bea0c8669f96794498fc37d9d18fe3f829d5
    Reviewed-on: https://gerrit.libreoffice.org/72467
    Tested-by: Jenkins
    Tested-by: Olivier Hallot <olivier.hallot at libreoffice.org>
    Reviewed-by: Olivier Hallot <olivier.hallot at libreoffice.org>

diff --git a/Package_html_static.mk b/Package_html_static.mk
index d1ebbbb1b..249783c22 100644
--- a/Package_html_static.mk
+++ b/Package_html_static.mk
@@ -17,6 +17,7 @@ $(eval $(call gb_Package_add_files,helpcontent2_html_static,$(LIBO_SHARE_HELP_FO
 $(eval $(call gb_Package_add_file,helpcontent2_html_static,$(LIBO_SHARE_HELP_FOLDER)$(if $(HELP_ONLINE),/$(PRODUCTVERSION))/index.html,index2.html))
 
 $(eval $(call gb_Package_add_files,helpcontent2_html_static,$(LIBO_SHARE_HELP_FOLDER)$(if $(HELP_ONLINE),/$(PRODUCTVERSION)),\
+	a11y-toggle.js \
 	default.css \
 	fuzzysort.js \
 	help.js \
diff --git a/help3xsl/a11y-toggle.js b/help3xsl/a11y-toggle.js
new file mode 100644
index 000000000..821a8e027
--- /dev/null
+++ b/help3xsl/a11y-toggle.js
@@ -0,0 +1,100 @@
+/*
+MIT License
+
+Copyright (c) 2016 Edenspiekermann
+
+*/
+
+(function () {
+  'use strict';
+
+  var internalId = 0;
+  var togglesMap = {};
+  var targetsMap = {};
+
+  function $ (selector, context) {
+    return Array.prototype.slice.call(
+      (context || document).querySelectorAll(selector)
+    );
+  }
+
+  function getClosestToggle (element) {
+    if (element.closest) {
+      return element.closest('[data-a11y-toggle]');
+    }
+
+    while (element) {
+      if (element.nodeType === 1 && element.hasAttribute('data-a11y-toggle')) {
+        return element;
+      }
+
+      element = element.parentNode;
+    }
+
+    return null;
+  }
+
+  function handleToggle (toggle) {
+    var target = toggle && targetsMap[toggle.getAttribute('aria-controls')];
+
+    if (!target) {
+      return false;
+    }
+
+    var toggles = togglesMap['#' + target.id];
+    var isExpanded = target.getAttribute('aria-hidden') === 'false';
+
+    target.setAttribute('aria-hidden', isExpanded);
+    toggles.forEach(function (toggle) {
+      toggle.setAttribute('aria-expanded', !isExpanded);
+    });
+  }
+
+  var initA11yToggle = function (context) {
+    togglesMap = $('[data-a11y-toggle]', context).reduce(function (acc, toggle) {
+      var selector = '#' + toggle.getAttribute('data-a11y-toggle');
+      acc[selector] = acc[selector] || [];
+      acc[selector].push(toggle);
+      return acc;
+    }, togglesMap);
+
+    var targets = Object.keys(togglesMap);
+    targets.length && $(targets).forEach(function (target) {
+      var toggles = togglesMap['#' + target.id];
+      var isExpanded = target.hasAttribute('data-a11y-toggle-open');
+      var labelledby = [];
+
+      toggles.forEach(function (toggle) {
+        toggle.id || toggle.setAttribute('id', 'a11y-toggle-' + internalId++);
+        toggle.setAttribute('aria-controls', target.id);
+        toggle.setAttribute('aria-expanded', isExpanded);
+        labelledby.push(toggle.id);
+      });
+
+      target.setAttribute('aria-hidden', !isExpanded);
+      target.hasAttribute('aria-labelledby') || target.setAttribute('aria-labelledby', labelledby.join(' '));
+
+      targetsMap[target.id] = target;
+    });
+  };
+
+  document.addEventListener('DOMContentLoaded', function () {
+    initA11yToggle();
+  });
+
+  document.addEventListener('click', function (event) {
+    var toggle = getClosestToggle(event.target);
+    handleToggle(toggle);
+  });
+
+  document.addEventListener('keyup', function (event) {
+    if (event.which === 13 || event.which === 32) {
+      var toggle = getClosestToggle(event.target);
+      if (toggle && toggle.getAttribute('role') === 'button') {
+        handleToggle(toggle);
+      }
+    }
+  });
+
+  window && (window.a11yToggle = initA11yToggle);
+})();
diff --git a/help3xsl/default.css b/help3xsl/default.css
index bf1358ee1..482f3ed6d 100644
--- a/help3xsl/default.css
+++ b/help3xsl/default.css
@@ -375,7 +375,11 @@ header {
     height: 60px;
     margin-right: 10px;
 }
-.lang nav, .modules nav {
+[aria-hidden='true'],
+[data-a11y-toggle]:not([aria-controls]) {
+  display: none;
+}
+#langs-nav:not([aria-hidden='true']), #modules-nav:not([aria-hidden='true']) {
     z-index: 100;
     /* line them up horizontally */
     display: flex;
@@ -386,7 +390,7 @@ header {
     /* make it smooth on iOS */
     -webkit-overflow-scrolling: touch;
 }
-.lang nav a, .modules nav a {
+#langs-nav a, #modules-nav a {
     color: #fff;
     background-color: #233336;
     display: block;
@@ -411,7 +415,6 @@ footer p {
     background-color: transparent !important;
     padding: 3px 0 0 0 !important;
 }
-.modules input[type=checkbox], .lang input[type=checkbox],
 .contents-treeview input[type=checkbox], aside input[type=checkbox] {
     position: absolute;
     opacity: 0;
@@ -604,7 +607,7 @@ li.disabled a {
     border-bottom: 2px solid #f3f3f3;
     background-color: #233336;
 }
-.modules label:after, .lang label:after {
+#modules:after, #langs:after {
     font-size: 30px;
     color: #fff;
     content:"⌄";
@@ -612,10 +615,10 @@ li.disabled a {
 .lang {
     background-color: #233336;
 }
-.lang label, .modules label {
+#langs, #modules {
     display: none;
 }
-.modules nav div {
+#modules-nav div {
     background-repeat: no-repeat;
     background-size: contain;
     float: left;
@@ -739,24 +742,30 @@ li.disabled a {
     }
 }
 @media screen and (min-width: 960px) {
-    .lang nav {
+    #langs-nav {
         display: none;
     }
-    .lang nav a {
+    #langs-nav a {
         font-size: 19px;
         white-space: normal;
     }
-    .lang label, .modules label {
+    /* these are buttons, so also reset some default stylings */
+    #langs, #modules {
         cursor: pointer;
         color: #fff;
         font-size: 19px;
         position: relative;
         top: 40px;
         display: block;
+        background: transparent;
+        border: none;
+        text-transform: none;
+        padding:0;
+        line-height: normal;
     }
-    /* change the menu direction to stacked */
 
-    .lang input[type="checkbox"]:checked ~ nav, .modules input[type="checkbox"]:checked ~ nav {
+    /* change the menu direction to stacked */
+    #langs-nav:not([aria-hidden='true']), #modules-nav:not([aria-hidden='true']) {
         display: flex;
         flex-direction: column;
         max-width: 120px;
@@ -766,17 +775,14 @@ li.disabled a {
         position: absolute;
         top: 80px;
     }
-    .modules input[type="checkbox"]:checked ~ nav {
+    #modules-nav {
         background-color: #101820;
         text-align: left;
     }
-    .modules nav {
-        display: none;
-    }
-    .modules nav div {
+    #modules-nav div {
         display: block;
     }
-    .modules nav a {
+    #modules-nav a {
         font-size: 19px;
     }
     aside {
diff --git a/help3xsl/help2.js b/help3xsl/help2.js
index f62105dc6..54dd195ab 100644
--- a/help3xsl/help2.js
+++ b/help3xsl/help2.js
@@ -217,10 +217,16 @@ debugInfo(getParameterByName("Debug"));
 
 // Mobile devices need the modules and langs on page load
 if (Math.max(document.documentElement.clientWidth, window.innerWidth || 0) < 960) {
-    var e = new Event('change');
-    var modules = document.getElementById('modules');
-    var langs = document.getElementById('langs');
-    modules.dispatchEvent(e);
-    langs.dispatchEvent(e);
+    var e = new Event('click');
+    var modulesBtn = document.getElementById('modules');
+    var langsBtn = document.getElementById('langs');
+    var modules = document.getElementById('modules-nav');
+    var langs = document.getElementById('langs-nav');
+    modules.setAttribute('data-a11y-toggle-open', '');
+    modulesBtn.dispatchEvent(e);
+    if (langs) {
+        langs.setAttribute('data-a11y-toggle-open', '');
+        langsBtn.dispatchEvent(e);
+    }
 }
 /* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s cinkeys+=0=break: */
diff --git a/help3xsl/online_transform.xsl b/help3xsl/online_transform.xsl
index 95d19bc56..2ca8deded 100644
--- a/help3xsl/online_transform.xsl
+++ b/help3xsl/online_transform.xsl
@@ -154,6 +154,7 @@
         <script type="text/javascript" src="{$target}fuzzysort.js"></script>
         <script type="text/javascript" src="{$target}prism.js"></script>
         <script type="text/javascript" src="{$target}help2.js" defer=""></script>
+        <script type="text/javascript" src="{$target}a11y-toggle.js" defer=""></script>
         <script type="text/javascript" src="{$target}{$lang}/langnames.js" defer=""></script>
         <script type="text/javascript" src="{$target}paginathing.js" defer=""></script>
         <script type="text/javascript" src="{$target}{$lang}/bookmarks.js" defer=""></script>
@@ -179,14 +180,16 @@
             </div>
         </header>
         <div class="modules">
-            <input id="modules" name="modules" type="checkbox" onchange="setupModules('{$target}', '{$lang}');"/>
-            <label for="modules"><xsl:value-of select="$ui_module"/></label>
+            <button type="button" data-a11y-toggle="modules-nav" id="modules" onclick="setupModules('{$target}', '{$lang}');">
+                <xsl:value-of select="$ui_module"/>
+            </button>
 	    <nav id="modules-nav"/><!-- is filled in via setupModules() on demand -->
         </div>
         <xsl:if test="$online">
             <div class="lang">
-                <input id="langs" name="language-menu" type="checkbox" onchange="setupLanguages('{$target}', '{$htmlpage}');"/>
-                <label for="langs"><xsl:value-of select="$ui_language"/></label>
+                <button type="button" data-a11y-toggle="langs-nav" id="langs" onclick="setupLanguages('{$target}', '{$htmlpage}');">
+                    <xsl:value-of select="$ui_language"/>
+                </button>
                 <nav id="langs-nav"/><!-- is filled in via setupLanguages() on demand -->
             </div>
         </xsl:if>


More information about the Libreoffice-commits mailing list