1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
content / test / data / accessibility / event / menubar-show-hide-menus.html [blame]
<!--
@AURALINUX-DENY:*
@AURALINUX-ALLOW:STATE-CHANGE:EXPANDED*
@AURALINUX-ALLOW:STATE-CHANGE:SHOWING*
@MAC-DENY:*
@MAC-ALLOW:AXExpandedChanged*
@MAC-ALLOW:AXMenu*
@WIN-DENY:*
@WIN-ALLOW:EVENT_OBJECT_STATECHANGE*
@WIN-ALLOW:EVENT_SYSTEM_MENUPOPUP*
@UIA-WIN-DENY:*
@UIA-WIN-ALLOW:ExpandCollapse*
@UIA-WIN-ALLOW:Menu*
@UIA-WIN-ALLOW:Name*
-->
<!DOCTYPE html>
<style>
ul { list-style-type: none;}
</style>
<ul role="menubar" id="menubar">
<li role="menuitem" id="file-menuitem" aria-haspopup="true" aria-label="File">File
<ul role="menu" id="file-menu" aria-label="File">
<li role="menuitem" id="new-menuitem" aria-haspopup="true" aria-label="New">New
<ul role="menu" id="new-menu" aria-label="New">
<li role="menuitem">Document</li>
<li role="menuitem">Spreadsheet</li>
<li role="menuitem">Presentation</li>
</ul>
</li>
<li role="menuitem">Open...</li>
<li role="menuitem">Quit</li>
</ul>
</li>
<li role="menuitem">About</li>
</ul>
<span id="status" tabindex="0"></span>
<script>
fileMenu = document.getElementById("file-menu");
fileMenuItem = document.getElementById("file-menuitem");
newMenu = document.getElementById("new-menu");
newMenuItem = document.getElementById("new-menuitem");
menubar = document.getElementById("menubar");
setInitialState();
function setInitialState() {
newMenu.style.display = "none";
newMenuItem.setAttribute("aria-expanded", "false");
fileMenu.style.display = "none";
fileMenuItem.setAttribute("aria-expanded", "false");
}
function updateStatus(string) {
document.getElementById("status").innerText = string;
}
function openFileMenu() {
fileMenu.style.display = "block";
fileMenuItem.setAttribute("aria-expanded", "true");
updateStatus("open file done");
}
function closeFileMenu() {
fileMenu.style.display = "none";
fileMenuItem.setAttribute("aria-expanded", "false");
}
function openNewMenu() {
newMenu.style.display = "block";
newMenuItem.setAttribute("aria-expanded", "true");
updateStatus("open new done");
}
function closeNewMenu() {
newMenu.style.display = "none";
newMenuItem.setAttribute("aria-expanded", "false");
}
function openFileAndNewMenus() {
// We don't call openFileMenu() and openNewMenu() here because those
// functions also call updateStatus() which might cause the event
// recorder to conclude it had obtained every event.
fileMenu.style.display = "block";
fileMenuItem.setAttribute("aria-expanded", "true");
newMenu.style.display = "block";
newMenuItem.setAttribute("aria-expanded", "true");
updateStatus("open file and new done");
}
function closeFileAndNewMenus() {
closeNewMenu();
closeFileMenu();
updateStatus("close file and new done");
}
function hideMenubar() {
menubar.style.display = "none";
updateStatus("hide menubar done");
}
function showMenubar() {
setInitialState();
menubar.style.display = "block";
updateStatus("show menubar done");
}
const go_passes = [
() => openFileAndNewMenus(),
() => closeFileAndNewMenus(),
// This should not generate any events because the parent container has
// display:none.
() => openNewMenu(),
// This should generate events for both menus, because functionally they
// are now both being displayed.
() => openFileMenu(),
// When the menubar is hidden, we want to be sure menus which fired events
// to notify they were showing also fire events notifying they were closed.
() => hideMenubar(),
// Unusual case. The file and new menu are still hidden because of the
// menubar parent, despite the fact that they are marked display:block.
// Here we mark the entire thing visible, which will make the menubar,
// file menu and new menu visible all at once. It's debatable whether
// menu events should be fired for the newly visible file and new menu.
// Previously we did not fire these events, and now we do.
() => showMenubar(),
];
var current_pass = 0;
function go() {
go_passes[current_pass++].call();
return current_pass < go_passes.length;
}
</script>