summaryrefslogtreecommitdiffstats
path: root/testing/web-platform/tests/editing/edit-context/edit-context-inheritability.tentative.html
blob: 59c553d966f19a3512aba1673f5a4117f2d9e970 (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
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
<!DOCTYPE html>
<html>
<head>
<title>EditContext: Inherited Editability</title>
<meta name="author" title="Dan Clark" href="mailto:daniec@microsoft.com">
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<script src="/resources/testdriver.js"></script>
<script src="/resources/testdriver-actions.js"></script>
<script src="/resources/testdriver-vendor.js"></script>
</head>
<body>
  <div id="edit-context-top-0">Text in EditContext-associated element, should be editable</div>

  <div id="edit-context-top-1">
    <div id="default-1">
      Element child of EditContext, should be editable
    </div>
  </div>

  <div id="edit-context-top-2">
    <div id="noteditable-2" contenteditable="false">
      <div id="editable-in-noteditable-2" contenteditable="">
        This is a contenteditable="" child of contenteditable="false" parent.
        This node should be editable. It should be the target of beforeinput/input events when the user edits here.
        The grandparent node #edit-context-0 should not be the target of beforeinput/input events,
        and the EditContext should not receive
        textupdate events
      </div>
    </div>
  </div>

  <div id="edit-context-top-3">
    <div id="noteditable-3" contenteditable="false">
      <div id="editable-in-noteditable-3" contenteditable="">
        <div id="contenteditable-in-contenteditable-3" contenteditable="">
          This is an contenteditable="" child of a contenteditable="". Since this is the child of an
          editable element, when the user types here, it's the parent contenteditable="" that gets
          input/beforeinput events, and this doesn't. Basically the child contenteditable="" attribute
          is a no-op.
        </div>
      </div>
    </div>
  </div>

  <div id="edit-context-top-4">
    <div id="noteditable-4" contenteditable="false">
      <div id="edit-context-in-noteditable-4">
        This is an EditContext child of contenteditable="false" parent.
        This node should be editable, and this EditContext (but not the
        grandparent EditContext) should get events, since there is an
        intermediate non-editable parent.
      </div>
    </div>
  </div>

  <div id="edit-context-top-5">
    <div id="contenteditable-in-ec-5" contenteditable="">
      This is a contenteditable="" child of EditContext.
      It inherits editability from the parent and it should not be the target of beforeinput/input events.
      Setting contenteditable="" on this node is basically a no-op.
    </div>
  </div>

  <div id="edit-context-top-6">
    <input id="input-in-ec-6" value="Input in EditContext. Events are fired against this element, and not against any parent EditContext.">
  </div>

  <div id="edit-context-top-7">
    <div id="edit-context-in-ec-7">
      EditContext child of EditContext. When user types here,
      events are fired only against the parent EditContext, not this one.
      Since the parent element was editable, the EditContext association is basically a no-op.
    </div>
  </div>

<script>
  const event_log = [];

  const editContextElements = document.querySelectorAll("div[id^='edit-context-']");
  editContextElements.forEach((element) => {
    element.editContext = new EditContext();
  });

  const divs = Array.from(document.querySelectorAll("div"));
  const inputs = Array.from(document.querySelectorAll("input"));
  const eventTargets = divs.concat(inputs);
  eventTargets.forEach((element) => {
    element.addEventListener("beforeinput", (e) => {
      if (element == e.target) {
        event_log.push(`beforeinput: ${element.id}`);
      }
    });

    element.addEventListener("input", (e) => {
      if (element === e.target) {
        event_log.push(`input: ${element.id}`);
      }
    });

    if (element.editContext) {
      element.editContext.addEventListener("textupdate", () => {
        event_log.push(`textupdate: ${element.id}`);
      });
    }
  });

  promise_test(async () => {
    event_log.length = 0;

    const input_target = document.querySelector("#edit-context-top-0");
    await test_driver.click(input_target);
    await test_driver.send_keys(input_target, "a");
    assert_array_equals(event_log, ["beforeinput: edit-context-top-0", "textupdate: edit-context-top-0"]);
  }, 'Check that element with EditContext is editable and gets events');

  promise_test(async () => {
    event_log.length = 0;

    const input_target = document.querySelector("#default-1");
    await test_driver.click(input_target);
    await test_driver.send_keys(input_target, "a");
    assert_array_equals(event_log, ["beforeinput: edit-context-top-1", "textupdate: edit-context-top-1"]);
  }, 'Check that child of EditContext is editable and the parent EditContext gets the events');

  promise_test(async () => {
    event_log.length = 0;

    const input_target = document.querySelector("#editable-in-noteditable-2");
    await test_driver.click(input_target);
    await test_driver.send_keys(input_target, "a");
    assert_array_equals(event_log, ["beforeinput: editable-in-noteditable-2", "input: editable-in-noteditable-2"]);
  }, 'Check that a contenteditable child of a contenteditable="false" is editable');

  promise_test(async () => {
    event_log.length = 0;

    const input_target = document.querySelector("#contenteditable-in-contenteditable-3");
    await test_driver.click(input_target);
    await test_driver.send_keys(input_target, "a");
    assert_array_equals(event_log, ["beforeinput: editable-in-noteditable-3", "input: editable-in-noteditable-3"]);
  }, 'Check that a contenteditable child of a contenteditable is editable, but the parent contenteditable gets the events');

  promise_test(async () => {
    event_log.length = 0;

    const input_target = document.querySelector("#edit-context-in-noteditable-4");
    await test_driver.click(input_target);
    await test_driver.send_keys(input_target, "a");
    assert_array_equals(event_log, ["beforeinput: edit-context-in-noteditable-4", "textupdate: edit-context-in-noteditable-4"]);
  }, 'Check that an EditContext child of a contenteditable="false" parent is editable and gets events');

  promise_test(async () => {
    event_log.length = 0;

    const input_target = document.querySelector("#contenteditable-in-ec-5");
    await test_driver.click(input_target);
    await test_driver.send_keys(input_target, "a");
    assert_array_equals(event_log, ["beforeinput: edit-context-top-5", "textupdate: edit-context-top-5"]);
  }, 'Check that an contenteditable child of an EditContext is editable, but the EditContext gets the events');

  promise_test(async () => {
    event_log.length = 0;

    const input_target = document.querySelector("#input-in-ec-6");
    await test_driver.click(input_target);
    await test_driver.send_keys(input_target, "a");
    assert_array_equals(event_log, ["beforeinput: input-in-ec-6", "input: input-in-ec-6"]);
  }, 'Check that an input element in an EditContext is the event target for beforeinput/input');

  promise_test(async () => {
    event_log.length = 0;

    const input_target = document.querySelector("#edit-context-in-ec-7");
    await test_driver.click(input_target);
    await test_driver.send_keys(input_target, "a");
    assert_array_equals(event_log, ["beforeinput: edit-context-top-7", "textupdate: edit-context-top-7"]);
  }, 'Check that for an EditContext child of an EditContext, the parent is the one that gets the events');

</script>
</body>
</html>