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
|
<!DOCTYPE html>
<meta charset="utf-8">
<link rel="author" href="mailto:masonf@chromium.org">
<link rel=help href="https://html.spec.whatwg.org/multipage/popover.html">
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<!-- Enumerate all the ways of creating an ancestor popover relationship -->
<div class="example">
<p>Direct DOM children</p>
<div popover class=ancestor><p>Ancestor popover</p>
<div popover class=child><p>Child popover</p></div>
</div>
</div>
<div class="example">
<p>Grandchildren</p>
<div popover class=ancestor><p>Ancestor popover</p>
<div>
<div>
<div popover class=child><p>Child popover</p></div>
</div>
</div>
</div>
</div>
<div class="example">
<p>popovertarget attribute relationship</p>
<div popover class=ancestor><p>Ancestor popover</p>
<button popovertarget=trigger1 class=clickme>Button</button>
</div>
<div id=trigger1 popover class=child><p>Child popover</p></div>
</div>
<div class="example">
<p>nested popovertarget attribute relationship</p>
<div popover class=ancestor><p>Ancestor popover</p>
<div>
<div>
<button popovertarget=trigger2 class=clickme>Button</button>
</div>
</div>
</div>
<div id=trigger2 popover class=child><p>Child popover</p></div>
</div>
<!-- Other examples -->
<button id=b1 onclick='p1.showPopover()'>Popover 1</button>
<div popover id=p1><p>This is popover #1</p>
<button id=b2 onclick='p2.showPopover()'>Popover 2</button>
<div popover id=p2><p>This is popover #2</p>
<button id=b3 onclick='p3.showPopover()'>Popover 3</button>
<div popover id=p3><p>This is popover #3</p></div>
</div>
</div>
<dialog id=d1>This is a dialog<button onclick='this.parentElement.close()'>Close</button></dialog>
<button id=b5 onclick='d1.showPopover()'>Dialog</button>
<script>
// Test basic ancestor relationships
for(let example of document.querySelectorAll('.example')) {
const descr = example.querySelector('p').textContent;
const ancestor = example.querySelector('[popover].ancestor');
const child = example.querySelector('[popover].child');
const clickToActivate = example.querySelector('.clickme');
test(function() {
assert_true(!!descr && !!ancestor && !!child);
assert_false(ancestor.matches(':popover-open'));
assert_false(child.matches(':popover-open'));
ancestor.showPopover();
if (clickToActivate)
clickToActivate.click();
else
child.showPopover();
assert_true(child.matches(':popover-open'));
assert_true(ancestor.matches(':popover-open'));
ancestor.hidePopover();
assert_false(ancestor.matches(':popover-open'));
assert_false(child.matches(':popover-open'));
},descr);
}
const popovers = [p1, p2, p3];
function assertState(...states) {
assert_equals(popovers.length,states.length);
for(let i=0;i<popovers.length;++i) {
assert_equals(popovers[i].matches(':popover-open'),states[i],`Popover #${i+1} incorrect state`);
}
}
test(function() {
function openManyPopovers() {
p1.showPopover();
p2.showPopover();
p3.showPopover();
assertState(true,true,true);
}
openManyPopovers();
d1.show(); // Dialog.show() should hide all popovers.
assertState(false,false,false);
d1.close();
openManyPopovers();
d1.showModal(); // Dialog.showModal() should also hide all popovers.
assertState(false,false,false);
d1.close();
}, "popovers should be closed by dialogs")
test(function() {
// Note: d1 is a <dialog> element, not a popover.
assert_false(d1.open);
d1.show();
assert_true(d1.open);
p1.showPopover();
assertState(true,false,false);
assert_true(d1.open);
p1.hidePopover();
assert_true(d1.open);
d1.close();
assert_false(d1.open);
}, "dialogs should not be closed by popovers")
</script>
<style>
#p1 { top:350px; }
#p2 { top:350px; left:200px; }
#p3 { top:500px; }
</style>
|