Browse Source

无障碍:首页结构读屏

任一存 3 years ago
parent
commit
d5a81dfa86
5 changed files with 68 additions and 32 deletions
  1. 6 3
      web/README.md
  2. 18 6
      web/src/utils.js
  3. 8 2
      web/src/views/Home/index.vue
  4. 3 3
      web/src/views/accessibility.vue
  5. 33 18
      web/src/views/layout/index.vue

File diff suppressed because it is too large
+ 6 - 3
web/README.md


+ 18 - 6
web/src/utils.js

@@ -17,6 +17,14 @@ function mapTags(tag) {
 }
 
 function extractTextForMagnify(e) {
+  const ariaLabel = e.path[0].getAttribute('aria-label')
+  if (e.path[0].getAttribute('aria-label')) {
+    return {
+      elemDisc: '',
+      elemContent: ariaLabel
+    }
+  }
+  
   // console.log(e)
   if (e.path[0].nodeName === 'HTML') {
     return
@@ -65,7 +73,7 @@ function isSameObject(object1, object2) {
   return true
 }
 
-function getAndFocusNextNodeWithClassName(className) {
+function getAndFocusNextNodeWithCustomAttribute(attriName) {
   const startNode = (document.activeElement || document.body)
 
   const treeWalker = document.createTreeWalker(document.body, NodeFilter.SHOW_ELEMENT)
@@ -80,14 +88,14 @@ function getAndFocusNextNodeWithClassName(className) {
       console.log('往下没找到')
       break
     }
-    if (nextNode.classList && [...nextNode.classList].some(item => item === className)) {
+    if (nextNode.dataset[attriName] !== undefined) {
       console.log('往下找到了')
       targetNode = nextNode
       break
     }
   }
 
-  if (!targetNode && startNode !== document.body) {
+  if (!targetNode && (startNode !== document.body)) {
     treeWalker.currentNode = document.body
     // eslint-disable-next-line
     while(true) {
@@ -96,8 +104,8 @@ function getAndFocusNextNodeWithClassName(className) {
         console.log('往上也没找到')
         break
       }
-      if (nextNode.classList && [...nextNode.classList].some(item => item === className)) {
-        console.log('上找到了')
+      if (nextNode.dataset[attriName] !== undefined) {
+        console.log('上找到了')
         targetNode = nextNode
         break
       }
@@ -106,6 +114,10 @@ function getAndFocusNextNodeWithClassName(className) {
 
   if (targetNode) {
     targetNode.focus()
+    if (document.activeElement !== targetNode) {
+      targetNode.setAttribute('tabindex', '0')
+      targetNode.focus()
+    }
   }
 
   return targetNode
@@ -197,5 +209,5 @@ export default {
   isSameObject,
   iterateOnFocusableNode,
   debounce,
-  getAndFocusNextNodeWithClassName,
+  getAndFocusNextNodeWithCustomAttribute,
 }

+ 8 - 2
web/src/views/Home/index.vue

@@ -1,7 +1,10 @@
 <template>
   <div class="Home">
     <!-- 轮播组件 -->
-    <el-carousel>
+    <el-carousel
+      data-aria-viewport-area tabindex="0"
+      aria-label="You've reached the slider section. This section has four image URLs. To browse the content, please use the tab key."
+    >
       <el-carousel-item v-for="item in 4" :key="item">
         <img
           :src="require(`@/assets/images/swiper${item}.jpg`)"
@@ -11,7 +14,10 @@
       </el-carousel-item>
     </el-carousel>
     <!-- 底部 -->
-    <div class="bottomNav">
+    <div
+      class="bottomNav" data-aria-viewport-area tabindex="0"
+      aria-label="You've reached the pop-up window section; this section contains four URLs; please use the tab key to go through the content."
+    >
       <div class="t1" @click="$router.push('/Layout/Visit/2')">
         <div class="title">
           <span>Reservation</span>

+ 3 - 3
web/src/views/accessibility.vue

@@ -669,11 +669,11 @@ export default {
           this.onClickMagnifier()
         }
       } else if (e.key === "1" && e.altKey && !e.ctrlKey && !e.shiftKey) {
-        utils.getAndFocusNextNodeWithClassName('aria-navigation-area')
+        utils.getAndFocusNextNodeWithCustomAttribute('ariaNavigationArea')
       } else if (e.key === "2" && e.altKey && !e.ctrlKey && !e.shiftKey) {
-        utils.getAndFocusNextNodeWithClassName('aria-viewport-area')
+        utils.getAndFocusNextNodeWithCustomAttribute('ariaViewportArea')
       } else if (e.key === "3" && e.altKey && !e.ctrlKey && !e.shiftKey) {
-        utils.getAndFocusNextNodeWithClassName('aria-interactive-area')
+        utils.getAndFocusNextNodeWithCustomAttribute('ariaInteractiveArea')
       }
     },
     loadStoredSettings() {

+ 33 - 18
web/src/views/layout/index.vue

@@ -8,7 +8,10 @@
           <h1 class="logo">
             <img src="@/assets/images/logo.png" alt="" />
           </h1>
-          <ul class="mainbav">
+          <ul
+            class="mainbav" tabindex="0" data-aria-navigation-area
+            aria-label="You have reached the horizontal menu at the top of the website. There are eight dropdown menus and 34 options in this section. To browse the content, please use the tab key."
+          >
             <li
               @click="skipOne(item.url)"
               :class="{ active: $route.meta.myName === item.name }"
@@ -39,7 +42,12 @@
           </ul>
         </div>
         <!-- 右侧的输入框 -->
-        <div class="search" @keyup.enter="search" v-if="!menaInd.includes('Search')">
+        <div
+          class="search" @keyup.enter="search" v-if="!menaInd.includes('Search')"
+          data-aria-interactive-area
+          aria-label="You've reached the seach field, please use the tab key to browse the content."
+          tabindex="0"
+        >
           <el-input
             placeholder="search..."
             suffix-icon="el-icon-search"
@@ -49,25 +57,13 @@
           <div class="btnn" @click="search"></div>
         </div>
       </div>
-      <!-- 固定的二维码和游戏 -->
-      <div class="rightNav">
-        <ul class="rightIco">
-          <li title="game">
-            <img src="@/assets/images/game.png" alt="" />
-          </li>
-          <li>
-            <img src="@/assets/images/code.png" alt="" />
-            <div>
-              <img src="@/assets/images/index_ewm1.png" alt="" />
-              <img src="@/assets/images/index_ewm.jpg" alt="" />
-            </div>
-          </li>
-        </ul>
-      </div>
       <!-- 嵌套路由 -->
       <Router-view />
       <!-- 底部固定栏 -->
-      <div class="footer">
+      <div
+        class="footer" data-aria-viewport-area tabindex="0"
+        aria-label="You've reached footer section at the bottom of the website. This section contains five URLs. To browse the content, please use the tab key."
+      >
         <div>
           <span
             @click="footTo(item.path)"
@@ -81,6 +77,24 @@
           100045, P.R.China.
         </p>
       </div>
+      <!-- 固定的二维码和游戏 -->
+      <div
+        class="rightNav" data-aria-viewport-area tabindex="0"
+        aria-label="You've reached the pop-up window section, which has one URL and one image. Please use the tab key to go through the information."
+      >
+        <ul class="rightIco">
+          <li title="game">
+            <img src="@/assets/images/game.png" alt="" />
+          </li>
+          <li>
+            <img src="@/assets/images/code.png" alt="" />
+            <div>
+              <img src="@/assets/images/index_ewm1.png" alt="" />
+              <img src="@/assets/images/index_ewm.jpg" alt="" />
+            </div>
+          </li>
+        </ul>
+      </div>
     </div>
   </div>
 </template>
@@ -210,6 +224,7 @@ export default {
       font-size: 14px;
       color: #fff;
       line-height: 60px;
+      overflow: hidden;
       & > li {
         cursor: pointer;
         float: left;