View Javadoc
1   /*
2    * Copyright (c) 2002-2025 Gargoyle Software Inc.
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    * https://www.apache.org/licenses/LICENSE-2.0
8    *
9    * Unless required by applicable law or agreed to in writing, software
10   * distributed under the License is distributed on an "AS IS" BASIS,
11   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12   * See the License for the specific language governing permissions and
13   * limitations under the License.
14   */
15  package org.htmlunit.javascript.host.html;
16  
17  import org.htmlunit.WebDriverTestCase;
18  import org.htmlunit.junit.BrowserRunner;
19  import org.htmlunit.junit.annotation.Alerts;
20  import org.junit.Test;
21  import org.junit.runner.RunWith;
22  import org.openqa.selenium.By;
23  import org.openqa.selenium.WebDriver;
24  import org.openqa.selenium.WebElement;
25  
26  /**
27   * Tests for {@link HTMLLabelElement}.
28   *
29   * @author Ahmed Ashour
30   * @author Daniel Gredler
31   * @author Marc Guillemot
32   * @author Frank Danek
33   * @author Ronald Brill
34   */
35  @RunWith(BrowserRunner.class)
36  public class HTMLLabelElementTest extends WebDriverTestCase {
37  
38      /**
39       * @throws Exception if the test fails
40       */
41      @Test
42      @Alerts("")
43      public void htmlForNone() throws Exception {
44          final String html = DOCTYPE_HTML
45              + "<html>\n"
46              + "  <head>\n"
47              + "    <script>\n"
48              + LOG_TITLE_FUNCTION
49              + "      function doTest() {\n"
50              + "        log(document.getElementById('label1').htmlFor);\n"
51              + "      }\n"
52              + "    </script>\n"
53              + "  </head>\n"
54              + "  <body onload='doTest()'>\n"
55              + "    <label id='label1'>Item</label>\n"
56              + "    <input type='text' id='text1'>\n"
57              + "  </body>\n"
58              + "</html>";
59  
60          loadPageVerifyTitle2(html);
61      }
62  
63      /**
64       * @throws Exception if the test fails
65       */
66      @Test
67      @Alerts("")
68      public void htmlForEmpty() throws Exception {
69          final String html = DOCTYPE_HTML
70              + "<html>\n"
71              + "  <head>\n"
72              + "    <script>\n"
73              + LOG_TITLE_FUNCTION
74              + "      function doTest() {\n"
75              + "        log(document.getElementById('label1').htmlFor);\n"
76              + "      }\n"
77              + "    </script>\n"
78              + "  </head>\n"
79              + "  <body onload='doTest()'>\n"
80              + "    <label id='label1' for=''>Item</label>\n"
81              + "    <input type='text' id='text1'>\n"
82              + "  </body>\n"
83              + "</html>";
84  
85          loadPageVerifyTitle2(html);
86      }
87  
88      /**
89       * @throws Exception if the test fails
90       */
91      @Test
92      @Alerts("unknown")
93      public void htmlForUnknown() throws Exception {
94          final String html = DOCTYPE_HTML
95              + "<html>\n"
96              + "  <head>\n"
97              + "    <script>\n"
98              + LOG_TITLE_FUNCTION
99              + "      function doTest() {\n"
100             + "        log(document.getElementById('label1').htmlFor);\n"
101             + "      }\n"
102             + "    </script>\n"
103             + "  </head>\n"
104             + "  <body onload='doTest()'>\n"
105             + "    <label id='label1' for='unknown'>Item</label>\n"
106             + "    <input type='text' id='text1'>\n"
107             + "  </body>\n"
108             + "</html>";
109 
110         loadPageVerifyTitle2(html);
111     }
112 
113     /**
114      * @throws Exception if the test fails
115      */
116     @Test
117     @Alerts("text1")
118     public void htmlForKnown() throws Exception {
119         final String html = DOCTYPE_HTML
120             + "<html>\n"
121             + "  <head>\n"
122             + "    <script>\n"
123             + LOG_TITLE_FUNCTION
124             + "      function doTest() {\n"
125             + "        log(document.getElementById('label1').htmlFor);\n"
126             + "      }\n"
127             + "    </script>\n"
128             + "  </head>\n"
129             + "  <body onload='doTest()'>\n"
130             + "    <label id='label1' for='text1'>Item</label>\n"
131             + "    <input type='text' id='text1'>\n"
132             + "  </body>\n"
133             + "</html>";
134 
135         loadPageVerifyTitle2(html);
136     }
137 
138     /**
139      * @throws Exception if the test fails
140      */
141     @Test
142     @Alerts({"unknown", "null", "null"})
143     public void htmlForSetToUnknown() throws Exception {
144         final String html = DOCTYPE_HTML
145             + "<html>\n"
146             + "  <head>\n"
147             + "    <script>\n"
148             + LOG_TITLE_FUNCTION
149             + "      function doTest() {\n"
150             + "        try {\n"
151             + "          document.getElementById('label1').htmlFor = 'unknown';\n"
152             + "        } catch(e) {"
153             + "          logEx(e);\n"
154             + "        }\n"
155             + "        log(document.getElementById('label1').htmlFor);\n"
156             + "        log(document.getElementById('label1').control);\n"
157             + "        log(document.getElementById('label1').form);\n"
158             + "      }\n"
159             + "    </script>\n"
160             + "  </head>\n"
161             + "  <body onload='doTest()'>\n"
162             + "    <label id='label1'>Item</label>\n"
163             + "    <form id='form1'>\n"
164             + "      <input type='text' id='text1'>\n"
165             + "    </form>\n"
166             + "  </body>\n"
167             + "</html>";
168 
169         loadPageVerifyTitle2(html);
170     }
171 
172     /**
173      * @throws Exception if the test fails
174      */
175     @Test
176     @Alerts({"div1", "null", "null"})
177     public void htmlForSetToNotLabelable() throws Exception {
178         final String html = DOCTYPE_HTML
179             + "<html>\n"
180             + "  <head>\n"
181             + "    <script>\n"
182             + LOG_TITLE_FUNCTION
183             + "      function doTest() {\n"
184             + "        try {\n"
185             + "          document.getElementById('label1').htmlFor = 'div1';\n"
186             + "        } catch(e) {"
187             + "          logEx(e);\n"
188             + "        }\n"
189             + "        log(document.getElementById('label1').htmlFor);\n"
190             + "        log(document.getElementById('label1').control);\n"
191             + "        log(document.getElementById('label1').form);\n"
192             + "      }\n"
193             + "    </script>\n"
194             + "  </head>\n"
195             + "  <body onload='doTest()'>\n"
196             + "    <label id='label1'>Item</label>\n"
197             + "    <form id='form1'>\n"
198             + "      <div id='div1'></div>\n"
199             + "    </form>\n"
200             + "  </body>\n"
201             + "</html>";
202 
203         loadPageVerifyTitle2(html);
204     }
205 
206     /**
207      * @throws Exception if the test fails
208      */
209     @Test
210     @Alerts({"text1", "[object HTMLInputElement]", "[object HTMLFormElement]"})
211     public void htmlForSetToLabelable() throws Exception {
212         final String html = DOCTYPE_HTML
213             + "<html>\n"
214             + "  <head>\n"
215             + "    <script>\n"
216             + LOG_TITLE_FUNCTION
217             + "      function doTest() {\n"
218             + "        try {\n"
219             + "          document.getElementById('label1').htmlFor = 'text1';\n"
220             + "        } catch(e) {"
221             + "          logEx(e);\n"
222             + "        }\n"
223             + "        log(document.getElementById('label1').htmlFor);\n"
224             + "        log(document.getElementById('label1').control);\n"
225             + "        log(document.getElementById('label1').form);\n"
226             + "      }\n"
227             + "    </script>\n"
228             + "  </head>\n"
229             + "  <body onload='doTest()'>\n"
230             + "    <label id='label1'>Item</label>\n"
231             + "    <form id='form1'>\n"
232             + "      <input type='text' id='text1'>\n"
233             + "    </form>\n"
234             + "  </body>\n"
235             + "</html>";
236 
237         loadPageVerifyTitle2(html);
238     }
239 
240     /**
241      * @throws Exception if the test fails
242      */
243     @Test
244     @Alerts("null")
245     public void controlNone() throws Exception {
246         final String html =
247               "  <label id='label1'>Item</label>\n"
248             + "  <input type='text' id='text1'>\n";
249 
250         loadPageVerifyTitle2(generateControlPage(html));
251     }
252 
253     /**
254      * @throws Exception if the test fails
255      */
256     @Test
257     @Alerts("null")
258     public void controlForEmpty() throws Exception {
259         final String html =
260               "  <label id='label1' for=''>Item</label>\n"
261             + "  <input type='text' id='text1'>\n";
262 
263         loadPageVerifyTitle2(generateControlPage(html));
264     }
265 
266     /**
267      * @throws Exception if the test fails
268      */
269     @Test
270     @Alerts("null")
271     public void controlForUnknown() throws Exception {
272         final String html =
273               "  <label id='label1' for='unknown'>Item</label>\n"
274             + "  <input type='text' id='text1'>\n";
275 
276         loadPageVerifyTitle2(generateControlPage(html));
277     }
278 
279     /**
280      * @throws Exception if the test fails
281      */
282     @Test
283     @Alerts("null")
284     public void controlForNotLabelable() throws Exception {
285         final String html =
286               "  <label id='label1' for='div1'>Item</label>\n"
287             + "  <div id='div1'></div>\n";
288 
289         loadPageVerifyTitle2(generateControlPage(html));
290     }
291 
292     /**
293      * @throws Exception if the test fails
294      */
295     @Test
296     @Alerts("[object HTMLButtonElement]:button1")
297     public void controlForButton() throws Exception {
298         final String html =
299               "  <label id='label1' for='button1'>Item</label>\n"
300             + "  <button id='button1'></button>\n";
301 
302         loadPageVerifyTitle2(generateControlPage(html));
303     }
304 
305     /**
306      * @throws Exception if the test fails
307      */
308     @Test
309     @Alerts("[object HTMLInputElement]:text1")
310     public void controlForInput() throws Exception {
311         final String html =
312               "  <label id='label1' for='text1'>Item</label>\n"
313             + "  <input type='text' id='text1'>\n";
314 
315         loadPageVerifyTitle2(generateControlPage(html));
316     }
317 
318     /**
319      * @throws Exception if the test fails
320      */
321     @Test
322     @Alerts("null")
323     public void controlForInputHidden() throws Exception {
324         final String html =
325               "  <label id='label1' for='hidden1'>Item</label>\n"
326             + "  <input type='hidden' id='hidden1'>\n";
327 
328         loadPageVerifyTitle2(generateControlPage(html));
329     }
330 
331     /**
332      * @throws Exception if the test fails
333      */
334     @Test
335     @Alerts("[object HTMLMeterElement]:meter1")
336     public void controlForMeter() throws Exception {
337         final String html =
338               "  <label id='label1' for='meter1'>Item</label>\n"
339             + "  <meter id='meter1'></meter>\n";
340 
341         loadPageVerifyTitle2(generateControlPage(html));
342     }
343 
344     /**
345      * @throws Exception if the test fails
346      */
347     @Test
348     @Alerts("[object HTMLOutputElement]:output1")
349     public void controlForOutput() throws Exception {
350         final String html =
351               "  <label id='label1' for='output1'>Item</label>\n"
352             + "  <output id='output1'></output>\n";
353 
354         loadPageVerifyTitle2(generateControlPage(html));
355     }
356 
357     /**
358      * @throws Exception if the test fails
359      */
360     @Test
361     @Alerts("[object HTMLProgressElement]:progress1")
362     public void controlForProgress() throws Exception {
363         final String html =
364               "  <label id='label1' for='progress1'>Item</label>\n"
365             + "  <progress id='progress1'></progress>\n";
366 
367         loadPageVerifyTitle2(generateControlPage(html));
368     }
369 
370     /**
371      * @throws Exception if the test fails
372      */
373     @Test
374     @Alerts("[object HTMLSelectElement]:select1")
375     public void controlForSelect() throws Exception {
376         final String html =
377               "  <label id='label1' for='select1'>Item</label>\n"
378             + "  <select id='select1'><option>Option</option></select>\n";
379 
380         loadPageVerifyTitle2(generateControlPage(html));
381     }
382 
383     /**
384      * @throws Exception if the test fails
385      */
386     @Test
387     @Alerts("[object HTMLTextAreaElement]:text1")
388     public void controlForTextArea() throws Exception {
389         final String html =
390               "  <label id='label1' for='text1'>Item</label>\n"
391             + "  <textarea id='text1'></textarea>\n";
392 
393         loadPageVerifyTitle2(generateControlPage(html));
394     }
395 
396     /**
397      * @throws Exception if the test fails
398      */
399     @Test
400     @Alerts("null")
401     public void controlNestedNotLabelable() throws Exception {
402         final String html =
403               "  <label id='label1'>Item\n"
404             + "    <div id='div1'></div>\n"
405             + "  </label>\n";
406 
407         loadPageVerifyTitle2(generateControlPage(html));
408     }
409 
410     /**
411      * @throws Exception if the test fails
412      */
413     @Test
414     @Alerts("[object HTMLButtonElement]:button1")
415     public void controlNestedButton() throws Exception {
416         final String html =
417               "  <label id='label1'>Item\n"
418             + "    <button id='button1'></button>\n"
419             + "    <button id='button2'></button>\n"
420             + "  </label>\n";
421 
422         loadPageVerifyTitle2(generateControlPage(html));
423     }
424 
425     /**
426      * @throws Exception if the test fails
427      */
428     @Test
429     @Alerts("[object HTMLInputElement]:text1")
430     public void controlNestedInput() throws Exception {
431         final String html =
432               "  <label id='label1'>Item\n"
433             + "    <input type='text' id='text1'>\n"
434             + "    <input type='text' id='text2'>\n"
435             + "  </label>\n";
436 
437         loadPageVerifyTitle2(generateControlPage(html));
438     }
439 
440     /**
441      * @throws Exception if the test fails
442      */
443     @Test
444     @Alerts("null")
445     public void controlNestedInputHidden() throws Exception {
446         final String html =
447               "  <label id='label1'>Item\n"
448             + "    <input type='hidden' id='hidden1'>\n"
449             + "    <input type='hidden' id='hidden2'>\n"
450             + "  </label>\n";
451 
452         loadPageVerifyTitle2(generateControlPage(html));
453     }
454 
455     /**
456      * @throws Exception if the test fails
457      */
458     @Test
459     @Alerts("[object HTMLMeterElement]:meter1")
460     public void controlNestedMeter() throws Exception {
461         final String html =
462               "  <label id='label1'>Item\n"
463             + "    <meter id='meter1'></meter>\n"
464             + "    <meter id='meter2'></meter>\n"
465             + "  </label>\n";
466 
467         loadPageVerifyTitle2(generateControlPage(html));
468     }
469 
470     /**
471      * @throws Exception if the test fails
472      */
473     @Test
474     @Alerts("[object HTMLOutputElement]:output1")
475     public void controlNestedOutput() throws Exception {
476         final String html =
477               "  <label id='label1'>Item\n"
478             + "    <output id='output1'></output>\n"
479             + "    <output id='output2'></output>\n"
480             + "  </label>\n";
481 
482         loadPageVerifyTitle2(generateControlPage(html));
483     }
484 
485     /**
486      * @throws Exception if the test fails
487      */
488     @Test
489     @Alerts("[object HTMLProgressElement]:progress1")
490     public void controlNestedProgress() throws Exception {
491         final String html =
492               "  <label id='label1'>Item\n"
493             + "    <progress id='progress1'></progress>\n"
494             + "    <progress id='progress2'></progress>\n"
495             + "  </label>\n";
496 
497         loadPageVerifyTitle2(generateControlPage(html));
498     }
499 
500     /**
501      * @throws Exception if the test fails
502      */
503     @Test
504     @Alerts("[object HTMLSelectElement]:select1")
505     public void controlNestedSelect() throws Exception {
506         final String html =
507               "  <label id='label1'>Item\n"
508             + "    <select id='select1'><option>Option</option></select>\n"
509             + "    <select id='select2'><option>Option</option></select>\n"
510             + "  </label>\n";
511 
512         loadPageVerifyTitle2(generateControlPage(html));
513     }
514 
515     /**
516      * @throws Exception if the test fails
517      */
518     @Test
519     @Alerts("[object HTMLTextAreaElement]:text1")
520     public void controlNestedTextArea() throws Exception {
521         final String html =
522               "  <label id='label1'>Item\n"
523             + "    <textarea id='text1'></textarea>\n"
524             + "    <textarea id='text2'></textarea>\n"
525             + "  </label>\n";
526 
527         loadPageVerifyTitle2(generateControlPage(html));
528     }
529 
530     /**
531      * @throws Exception if the test fails
532      */
533     @Test
534     @Alerts("[object HTMLInputElement]:text2")
535     public void controlForVersusNested() throws Exception {
536         final String html =
537               "  <label id='label1' for='text2'>Item\n"
538             + "    <input type='text' id='text1'>\n"
539             + "  </label>\n"
540             + "  <input type='text' id='text2'>\n";
541 
542         loadPageVerifyTitle2(generateControlPage(html));
543     }
544 
545     /**
546      * @throws Exception if the test fails
547      */
548     @Test
549     @Alerts("null")
550     public void controlForUnknownVersusNested() throws Exception {
551         final String html =
552               "  <label id='label1' for='unknown'>Item\n"
553             + "    <input type='text' id='text1'>\n"
554             + "  </label>\n"
555             + "  <input type='text' id='text2'>\n";
556 
557         loadPageVerifyTitle2(generateControlPage(html));
558     }
559 
560     /**
561      * @throws Exception if the test fails
562      */
563     @Test
564     @Alerts("null")
565     public void controlForNotLabelableVersusNested() throws Exception {
566         final String html =
567               "  <label id='label1' for='div1'>Item\n"
568             + "    <input type='text' id='text1'>\n"
569             + "  </label>\n"
570             + "  <div id='div1'></div>\n";
571 
572         loadPageVerifyTitle2(generateControlPage(html));
573     }
574 
575     private static String generateControlPage(final String snippet) {
576         return DOCTYPE_HTML
577             + "<html>\n"
578             + "  <head>\n"
579             + "    <script>\n"
580             + LOG_TITLE_FUNCTION
581             + "      function dump(e) {\n"
582             + "        log(e + (e ? ':' + e.id : ''));\n"
583             + "      }\n"
584             + "    </script>\n"
585             + "  </head>\n"
586             + "  <body onload='dump(document.getElementById(\"label1\").control)'>\n"
587             + snippet
588             + "  </body>\n"
589             + "</html>";
590     }
591 
592     /**
593      * @throws Exception if the test fails
594      */
595     @Test
596     @Alerts("null")
597     public void controlSet() throws Exception {
598         final String html = DOCTYPE_HTML
599             + "<html>\n"
600             + "  <head>\n"
601             + "    <script>\n"
602             + LOG_TITLE_FUNCTION
603             + "      function doTest() {\n"
604             + "        try {\n"
605             + "          document.getElementById('label1').control = document.getElementById('text1');\n"
606             + "        } catch(e) {"
607             + "          logEx(e);\n"
608             + "        }\n"
609             + "        log(document.getElementById('label1').control);\n"
610             + "      }\n"
611             + "    </script>\n"
612             + "  </head>\n"
613             + "  <body onload='doTest()'>\n"
614             + "    <label id='label1'>Item</label>\n"
615             + "    <input type='text' id='text1'>\n"
616             + "  </body>\n"
617             + "</html>";
618 
619         loadPageVerifyTitle2(html);
620     }
621 
622     /**
623      * @throws Exception if the test fails
624      */
625     @Test
626     @Alerts("null")
627     public void formNoForm() throws Exception {
628         final String html
629             = "  <label id='label1'>Item</label>\n"
630             + "  <input type='text' id='text1'>\n";
631 
632         loadPageVerifyTitle2(generateFormPage(html));
633     }
634 
635     /**
636      * @throws Exception if the test fails
637      */
638     @Test
639     @Alerts("null")
640     public void formOutsideForm() throws Exception {
641         final String html
642             = "  <label id='label1'>Item</label>\n"
643             + "  <form id='form1'>\n"
644             + "    <input type='text' id='text1'>\n"
645             + "  </form>\n";
646 
647         loadPageVerifyTitle2(generateFormPage(html));
648     }
649 
650     /**
651      * @throws Exception if the test fails
652      */
653     @Test
654     @Alerts("null")
655     public void formInsideForm() throws Exception {
656         final String html
657             = "  <form id='form1'>\n"
658             + "    <label id='label1'>Item</label>\n"
659             + "    <input type='text' id='text1'>\n"
660             + "  </form>\n";
661 
662         loadPageVerifyTitle2(generateFormPage(html));
663     }
664 
665     /**
666      * @throws Exception if the test fails
667      */
668     @Test
669     @Alerts("null")
670     public void formForLabelableOutsideForm() throws Exception {
671         final String html
672             = "  <label id='label1' for='text1'>Item</label>\n"
673             + "  <input type='text' id='text1'>\n"
674             + "  <form id='form1'>\n"
675             + "    <input type='text' id='text2'>\n"
676             + "  </form>\n";
677 
678         loadPageVerifyTitle2(generateFormPage(html));
679     }
680 
681     /**
682      * @throws Exception if the test fails
683      */
684     @Test
685     @Alerts("null")
686     public void formForNotLabelableInsideForm() throws Exception {
687         final String html
688             = "  <label id='label1' for='div1'>Item</label>\n"
689             + "  <form id='form1'>\n"
690             + "    <div id='div1'></div>\n"
691             + "  </form>\n";
692 
693         loadPageVerifyTitle2(generateFormPage(html));
694     }
695 
696     /**
697      * @throws Exception if the test fails
698      */
699     @Test
700     @Alerts("[object HTMLFormElement]:form1")
701     public void formForLabelableInsideForm() throws Exception {
702         final String html
703             = "  <label id='label1' for='text1'>Item</label>\n"
704             + "  <form id='form1'>\n"
705             + "    <input type='text' id='text1'>\n"
706             + "  </form>\n";
707 
708         loadPageVerifyTitle2(generateFormPage(html));
709     }
710 
711     /**
712      * @throws Exception if the test fails
713      */
714     @Test
715     @Alerts("null")
716     public void formNestedLabelableOutsideForm() throws Exception {
717         final String html
718             = "  <label id='label1'>Item\n"
719             + "    <input type='text' id='text1'>\n"
720             + "  </label>\n"
721             + "  <form id='form1'>\n"
722             + "    <input type='text' id='text2'>\n"
723             + "  </form>\n";
724 
725         loadPageVerifyTitle2(generateFormPage(html));
726     }
727 
728     /**
729      * @throws Exception if the test fails
730      */
731     @Test
732     @Alerts("null")
733     public void formNestedNotLabelableInsideForm() throws Exception {
734         final String html
735             = "  <form id='form1'>\n"
736             + "    <label id='label1'>Item\n"
737             + "      <div id='div1'></div>\n"
738             + "    </label>\n"
739             + "  </form>\n";
740 
741         loadPageVerifyTitle2(generateFormPage(html));
742     }
743 
744     /**
745      * @throws Exception if the test fails
746      */
747     @Test
748     @Alerts("[object HTMLFormElement]:form1")
749     public void formNestedLabelableInsideForm() throws Exception {
750         final String html
751             = "  <form id='form1'>\n"
752             + "    <label id='label1'>Item\n"
753             + "      <input type='text' id='text1'>\n"
754             + "    </label>\n"
755             + "  </form>\n";
756 
757         loadPageVerifyTitle2(generateFormPage(html));
758     }
759 
760     private static String generateFormPage(final String snippet) {
761         return DOCTYPE_HTML
762             + "<html>\n"
763             + "  <head>\n"
764             + "    <script>\n"
765             + LOG_TITLE_FUNCTION
766             + "      function dump(e) {\n"
767             + "        log(e + (e ? ':' + e.id : ''));\n"
768             + "      }\n"
769             + "      function doTest() {\n"
770             + "        dump(document.getElementById('label1').form);\n"
771             + "      }\n"
772             + "    </script>\n"
773             + "  </head>\n"
774             + "  <body onload='doTest()'>\n"
775             + snippet
776             + "  </body>\n"
777             + "</html>";
778     }
779 
780     /**
781      * @throws Exception if the test fails
782      */
783     @Test
784     @Alerts("null")
785     public void formSet() throws Exception {
786         final String html = DOCTYPE_HTML
787             + "<html>\n"
788             + "  <head>\n"
789             + "    <script>\n"
790             + LOG_TITLE_FUNCTION
791             + "      function doTest() {\n"
792             + "        try {\n"
793             + "          document.getElementById('label1').form = document.getElementById('form1');\n"
794             + "        } catch(e) {"
795             + "          logEx(e);\n"
796             + "        }\n"
797             + "        log(document.getElementById('label1').form);\n"
798             + "      }\n"
799             + "    </script>\n"
800             + "  </head>\n"
801             + "  <body onload='doTest()'>\n"
802             + "    <label id='label1'>Item</label>\n"
803             + "    <form id='form1'>\n"
804             + "      <input type='text' id='text1'>\n"
805             + "    </form>\n"
806             + "  </body>\n"
807             + "</html>";
808 
809         loadPageVerifyTitle2(html);
810     }
811 
812     /**
813      * @throws Exception if the test fails
814      */
815     @Test
816     public void clickAfterHtmlForSetByJS() throws Exception {
817         final String html = DOCTYPE_HTML
818             + "<html>\n"
819             + "  <head>\n"
820             + "    <script>\n"
821             + "      function doTest() {\n"
822             + "        document.getElementById('label1').htmlFor = 'checkbox1';\n"
823             + "      }\n"
824             + "    </script>\n"
825             + "  </head>\n"
826             + "  <body onload='doTest()'>\n"
827             + "    <label id='label1'>Item</label>\n"
828             + "    <input type='checkbox' id='checkbox1'>\n"
829             + "  </body>\n"
830             + "</html>";
831 
832         final WebDriver driver = loadPage2(html);
833         final WebElement checkbox = driver.findElement(By.id("checkbox1"));
834         assertFalse(checkbox.isSelected());
835         driver.findElement(By.id("label1")).click();
836         assertTrue(checkbox.isSelected());
837     }
838 
839     /**
840      * @throws Exception if the test fails
841      */
842     @Test
843     public void clickAfterNestedByJS() throws Exception {
844         final String html = DOCTYPE_HTML
845             + "<html>\n"
846             + "  <head>\n"
847             + "    <script>\n"
848             + "      function doTest() {\n"
849             + "        document.getElementById('label1').appendChild(document.getElementById('checkbox1'));\n"
850             + "      }\n"
851             + "    </script>\n"
852             + "  </head>\n"
853             + "  <body onload='doTest()'>\n"
854             + "    <label id='label1'>Item</label>\n"
855             + "    <input type='checkbox' id='checkbox1'>\n"
856             + "  </body>\n"
857             + "</html>";
858 
859         final WebDriver driver = loadPage2(html);
860         final WebElement checkbox = driver.findElement(By.id("checkbox1"));
861         assertFalse(checkbox.isSelected());
862         driver.findElement(By.id("label1")).click();
863         assertTrue(checkbox.isSelected());
864     }
865 
866     /**
867      * @throws Exception if the test fails
868      */
869     @Test
870     public void clickByJSAfterHtmlForSetByJS() throws Exception {
871         final String html = DOCTYPE_HTML
872             + "<html>\n"
873             + "  <head>\n"
874             + "    <script>\n"
875             + "      function doTest() {\n"
876             + "        document.getElementById('label1').htmlFor = 'checkbox1';\n"
877             + "      }\n"
878             + "      function delegateClick() {\n"
879             + "        try {\n"
880             + "          document.getElementById('label1').click();\n"
881             + "        } catch(e) {}\n"
882             + "      }\n"
883             + "    </script>\n"
884             + "  </head>\n"
885             + "  <body onload='doTest()'>\n"
886             + "    <label id='label1'>My Label</label>\n"
887             + "    <input type='checkbox' id='checkbox1'><br>\n"
888             + "    <input type=button id='button1' value='Test' onclick='delegateClick()'>\n"
889             + "  </body>\n"
890             + "</html>";
891 
892         final WebDriver driver = loadPage2(html);
893         final WebElement checkbox = driver.findElement(By.id("checkbox1"));
894         assertFalse(checkbox.isSelected());
895         driver.findElement(By.id("button1")).click();
896         assertTrue(checkbox.isSelected());
897     }
898 
899     /**
900      * @throws Exception if the test fails
901      */
902     @Test
903     public void clickByJSAfterNestedByJS() throws Exception {
904         final String html = DOCTYPE_HTML
905             + "<html>\n"
906             + "  <head>\n"
907             + "    <script>\n"
908             + "      function doTest() {\n"
909             + "        document.getElementById('label1').appendChild(document.getElementById('checkbox1'));\n"
910             + "      }\n"
911             + "      function delegateClick() {\n"
912             + "        try {\n"
913             + "          document.getElementById('label1').click();\n"
914             + "        } catch(e) {}\n"
915             + "      }\n"
916             + "    </script>\n"
917             + "  </head>\n"
918             + "  <body onload='doTest()'>\n"
919             + "    <label id='label1'>My Label</label>\n"
920             + "    <input type='checkbox' id='checkbox1'><br>\n"
921             + "    <input type=button id='button1' value='Test' onclick='delegateClick()'>\n"
922             + "  </body>\n"
923             + "</html>";
924 
925         final WebDriver driver = loadPage2(html);
926         final WebElement checkbox = driver.findElement(By.id("checkbox1"));
927         assertFalse(checkbox.isSelected());
928         driver.findElement(By.id("button1")).click();
929         assertTrue(checkbox.isSelected());
930     }
931 
932     /**
933      * @throws Exception if an error occurs
934      */
935     @Test
936     @Alerts({ "", "A", "a", "A", "a8", "8Afoo", "8", "@" })
937     public void accessKey() throws Exception {
938         final String html = DOCTYPE_HTML
939             + "<html>\n"
940             + "  <body>\n"
941             + "    <label id='a1'>a1</label>\n"
942             + "    <label id='a2' accesskey='A'>a2</label>\n"
943             + "    <script>\n"
944             + LOG_TITLE_FUNCTION
945             + "      var a1 = document.getElementById('a1'), a2 = document.getElementById('a2');\n"
946             + "      log(a1.accessKey);\n"
947             + "      log(a2.accessKey);\n"
948             + "      a1.accessKey = 'a';\n"
949             + "      a2.accessKey = 'A';\n"
950             + "      log(a1.accessKey);\n"
951             + "      log(a2.accessKey);\n"
952             + "      a1.accessKey = 'a8';\n"
953             + "      a2.accessKey = '8Afoo';\n"
954             + "      log(a1.accessKey);\n"
955             + "      log(a2.accessKey);\n"
956             + "      a1.accessKey = '8';\n"
957             + "      a2.accessKey = '@';\n"
958             + "      log(a1.accessKey);\n"
959             + "      log(a2.accessKey);\n"
960             + "    </script>\n"
961             + "  </body>\n"
962             + "</html>";
963 
964         loadPageVerifyTitle2(html);
965     }
966 }