summaryrefslogtreecommitdiffstats
path: root/dom/tests/mochitest/webcomponents/test_custom_element_in_shadow.html
blob: 504140648b37be7387e9cdde580c3676eafe7c18 (plain)
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
<!DOCTYPE HTML>
<html>
<!--
https://bugzilla.mozilla.org/show_bug.cgi?id=1087460
-->
<head>
  <title>Test for custom element callbacks in shadow DOM.</title>
  <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
</head>
<body>
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=1087460">Bug 1087460</a>
<div id="container"></div>

<script>

// Test callback for custom element when used after registration.

var createdCallbackCount = 0;
var attachedCallbackCount = 0;
var detachedCallbackCount = 0;
var attributeChangedCallbackCount = 0;

var p1 = Object.create(HTMLElement.prototype);

p1.createdCallback = function() {
  createdCallbackCount++;
};

p1.attachedCallback = function() {
  attachedCallbackCount++;
};

p1.detachedCallback = function() {
  detachedCallbackCount++;
};

p1.attributeChangedCallback = function(name, oldValue, newValue) {
  attributeChangedCallbackCount++;
};

document.registerElement("x-foo", { prototype: p1 });

var container = document.getElementById("container");
var shadow = container.createShadowRoot();

is(createdCallbackCount, 0, "createdCallback should not be called more than once in this test.");
var customElem = document.createElement("x-foo");
is(createdCallbackCount, 1, "createdCallback should be called after creating custom element.");

is(attributeChangedCallbackCount, 0, "attributeChangedCallback should not be called after just creating an element.");
customElem.setAttribute("data-foo", "bar");
is(attributeChangedCallbackCount, 1, "attributeChangedCallback should be called after setting an attribute.");

is(attachedCallbackCount, 0, "attachedCallback should not be called on an element that is not in a document/composed document.");
shadow.appendChild(customElem);
is(attachedCallbackCount, 1, "attachedCallback should be called after attaching custom element to the composed document.");

is(detachedCallbackCount, 0, "detachedCallback should not be called without detaching custom element.");
shadow.removeChild(customElem);
is(detachedCallbackCount, 1, "detachedCallback should be called after detaching custom element from the composed document.");

// Test callback for custom element already in the composed doc when created.

createdCallbackCount = 0;
attachedCallbackCount = 0;
detachedCallbackCount = 0;
attributeChangedCallbackCount = 0;

shadow.innerHTML = "<x-foo></x-foo>";
is(createdCallbackCount, 1, "createdCallback should be called after creating a custom element.");
is(attachedCallbackCount, 1, "attachedCallback should be called after creating an element in the composed document.");

shadow.innerHTML = "";
is(detachedCallbackCount, 1, "detachedCallback should be called after detaching custom element from the composed document.");

// Test callback for custom element in shadow DOM when host attached/detached to/from document.

createdCallbackCount = 0;
attachedCallbackCount = 0;
detachedCallbackCount = 0;
attributeChangedCallbackCount = 0;

var host = document.createElement("div");
shadow = host.createShadowRoot();
customElem = document.createElement("x-foo");

is(attachedCallbackCount, 0, "attachedCallback should not be called on newly created element.");
shadow.appendChild(customElem);
is(attachedCallbackCount, 0, "attachedCallback should not be called on attaching to a tree that is not in the composed document.");

is(attachedCallbackCount, 0, "detachedCallback should not be called.");
shadow.removeChild(customElem);
is(detachedCallbackCount, 0, "detachedCallback should not be called when detaching from a tree that is not in the composed document.");

shadow.appendChild(customElem);
is(attachedCallbackCount, 0, "attachedCallback should still not be called after reattaching to a shadow tree that is not in the composed document.");

container.appendChild(host);
is(attachedCallbackCount, 1, "attachedCallback should be called after host is inserted into document.");

container.removeChild(host);
is(detachedCallbackCount, 1, "detachedCallback should be called after host is removed from document.");

// Test callback for custom element for upgraded element.

createdCallbackCount = 0;
attachedCallbackCount = 0;
detachedCallbackCount = 0;
attributeChangedCallbackCount = 0;

shadow = container.shadowRoot;
shadow.innerHTML = "<x-bar></x-bar>";

var p2 = Object.create(HTMLElement.prototype);

p2.createdCallback = function() {
  createdCallbackCount++;
};

p2.attachedCallback = function() {
  attachedCallbackCount++;
};

document.registerElement("x-bar", { prototype: p2 });
is(createdCallbackCount, 1, "createdCallback should be called after registering element.");
is(attachedCallbackCount, 1, "attachedCallback should be called after upgrading element in composed document.");

</script>

</body>
</html>