• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Copyright 2016 The Chromium OS Authors. All rights reserved.
2# Use of this source code is governed by a BSD-style license that can be
3# found in the LICENSE file.
4
5import os
6
7from autotest_lib.client.bin import test
8from autotest_lib.client.bin import utils
9from autotest_lib.client.common_lib import error
10from autotest_lib.client.cros.input_playback import input_playback
11
12
13class a11y_test_base(test.test):
14    """Base class for a11y tests."""
15    version = 1
16
17    # ChromeVox extension id
18    _CHROMEVOX_ID = 'mndnfokpggljbaajbnioimlmbfngpief'
19    _CVOX_STATE_TIMEOUT = 40
20    _CVOX_INDICATOR_TIMEOUT = 40
21
22
23    def warmup(self):
24        """Test setup."""
25        # Emulate a keyboard for later ChromeVox toggle (if needed).
26        # See input_playback. The keyboard is used to play back shortcuts.
27        self._player = input_playback.InputPlayback()
28        self._player.emulate(input_type='keyboard')
29        self._player.find_connected_inputs()
30
31
32    def _child_test_cleanup(self):
33        """Can be overwritten by child classes and run duing parent cleanup."""
34        return
35
36
37    def cleanup(self):
38        self._player.close()
39        self._child_test_cleanup()
40
41
42    def _toggle_chromevox(self):
43        """Use keyboard shortcut and emulated keyboard to toggle ChromeVox."""
44        self._player.blocking_playback_of_default_file(
45                input_type='keyboard', filename='keyboard_ctrl+alt+z')
46
47    def _chromevox_move(self, direction):
48        """Use ChromeVox move commands (search + arrow key).
49
50        @param direction:  The direction in which to move, e.g. 'down'.
51
52        """
53        self._player.blocking_playback_of_default_file(
54                input_type='keyboard',
55                filename='keyboard_search+%s' % direction)
56
57    def _set_feature(self, feature, value):
58        """Set given feature to given value using a11y API call.
59
60        Presupposes self._extension (with accessibilityFeatures enabled).
61
62        @param feature: string of accessibility feature to change.
63        @param value: boolean of expected value.
64
65        @raises: error.TestError if feature cannot be set.
66
67        """
68        value_str = 'true' if value else 'false'
69        cmd = ('window.__result = null;\n'
70               'chrome.accessibilityFeatures.%s.set({value: %s});\n'
71               'chrome.accessibilityFeatures.%s.get({}, function(d) {'
72               'window.__result = d[\'value\']; });' % (
73                       feature, value_str, feature))
74        self._extension.ExecuteJavaScript(cmd)
75
76        poll_cmd = 'window.__result == %s;' % value_str
77        utils.poll_for_condition(
78                lambda: self._extension.EvaluateJavaScript(poll_cmd),
79                exception = error.TestError(
80                        'Timeout while trying to set %s to %s' %
81                        (feature, value_str)))
82
83
84    def _get_chromevox_state(self):
85        """Return whether ChromeVox is enabled or not.
86
87        Presupposes self._extension (with management enabled).
88
89        @returns: value of management.get.enabled.
90
91        @raises: error.TestError if state cannot be determined.
92
93        """
94        cmd = ('window.__enabled = null;\n'
95               'chrome.management.get(\'%s\', function(r) {'
96               'if (r) {window.__enabled = r[\'enabled\'];} '
97               'else {window.__enabled = false;}});' % self._CHROMEVOX_ID)
98        self._extension.ExecuteJavaScript(cmd)
99
100        poll_cmd = 'window.__enabled != null;'
101        utils.poll_for_condition(
102                lambda: self._extension.EvaluateJavaScript(poll_cmd),
103                exception=error.TestError(
104                        'ChromeVox: management.get.enabled was not set!'))
105        return self._extension.EvaluateJavaScript('window.__enabled')
106
107
108    def _confirm_chromevox_state(self, value):
109        """Fail test unless ChromeVox state is given value.
110
111        Presupposes self._extension (with management enabled).
112
113        @param value: True or False, whether ChromeVox should be enabled.
114
115        @raises: error.TestFail if actual state doesn't match expected.
116
117        """
118        utils.poll_for_condition(
119                lambda: self._get_chromevox_state() == value,
120                exception=error.TestFail('ChromeVox: enabled state '
121                                         'was not %s.' % value),
122                timeout=self._CVOX_STATE_TIMEOUT)
123
124
125    def _get_extension_path(self):
126        """Return the path to the default accessibility extension.
127
128        @returns: string of path to default extension.
129
130        """
131        this_dir = os.path.dirname(__file__)
132        return os.path.join(this_dir, 'a11y_ext')
133