<!doctype html>
<html>
  <head>
    <title>Pointer Event: Boundary compatibility events for multiple primary pointers</title>
    <meta content="text/html; charset=UTF-8" http-equiv="Content-Type"/>
    <link rel="author" title="Google" href="http://www.google.com "/>
    <meta name="assert" content="When more than one primary pointers are active, each will have an independent sequence of pointer boundary events but the compatibilty mouse boundary events have their own sequence."/>
    <link rel="stylesheet" type="text/css" href="pointerevent_styles.css">
    <script src="/resources/testharness.js"></script>
    <script src="/resources/testharnessreport.js"></script>
    <script type="text/javascript" src="pointerevent_support.js"></script>
    <script type="text/javascript">
      var test_pointerEvent = async_test("Multi-pointer boundary compat events");
      add_completion_callback(end_of_test);

      var detected_pointertypes = {};
      var event_log = [];

      // These two ids help us detect two different pointing devices.
      var first_entry_pointer_id = -1;
      var second_entry_pointer_id = -1;

      // Current node for each pointer id
      var current_node_for_id = {};

      function end_of_test() {
          showLoggedEvents();
          showPointerTypes();
      }

      function end_of_interaction() {
          test(function () {
              assert_equals(event_log.join(", "),
                  "mouseover@target0, mouseenter@target0, mouseout@target0, mouseleave@target0, " +
                  "mouseover@target1, mouseenter@target1, mouseout@target1, mouseleave@target1, " +
                  "mouseover@target0, mouseenter@target0, mouseout@target0, mouseleave@target0"
              );
          }, "Event log");

          test_pointerEvent.done(); // complete test
      }

      function log_event(label) {
          event_log.push(label);
      }

      function run() {
          on_event(document.getElementById("done"), "click", end_of_interaction);

          var target_list = ["target0", "target1"];
          var pointer_event_list = ["pointerenter", "pointerleave", "pointerover", "pointerout", "pointerdown"];
          var mouse_event_list = ["mouseenter", "mouseleave", "mouseover", "mouseout"];

          target_list.forEach(function(targetId) {
              var target = document.getElementById(targetId);

              pointer_event_list.forEach(function(eventName) {
                  on_event(target, eventName, function (event) {
                      var label = event.type + "@" + targetId;

                      detected_pointertypes[event.pointerType] = true;

                      if (!event.isPrimary) {
                          test(function () {
                              assert_unreached("Non-primary pointer " + label);
                          }, "Non-primary pointer " + label);
                      }

                      if (event.type === "pointerenter") {
                          var pointer_id = event.pointerId;
                          if (current_node_for_id[pointer_id] !== undefined) {
                              test(function () {
                                  assert_unreached("Double entry " + label);
                              }, "Double entry " + label);
                          }
                          current_node_for_id[pointer_id] = event.target;

                          // Test that two different pointing devices are used
                          if (first_entry_pointer_id === -1) {
                              first_entry_pointer_id = pointer_id;
                          } else if (second_entry_pointer_id === -1) {
                              second_entry_pointer_id = pointer_id;
                              test(function () {
                                  assert_not_equals(first_entry_pointer_id, second_entry_pointer_id);
                              }, "Different pointing devices");
                          }
                      } else if (event.type === "pointerleave") {
                          var pointer_id = event.pointerId;
                          if (current_node_for_id[pointer_id] !== event.target) {
                              test(function () {
                                  assert_unreached("Double exit " + label);
                              }, "Double exit " + label);
                          }
                          current_node_for_id[pointer_id] = undefined;
                      }
                  });
              });

              mouse_event_list.forEach(function(eventName) {
                  on_event(target, eventName, function (event) {
                      log_event(event.type + "@" + targetId);
                  });
              });
          });
      }
    </script>
    <style>
      #target0, #target1 {
        margin: 20px;
      }

      #done {
        margin: 20px;
        border: 2px solid black;
      }
  </style>
  </head>
  <body onload="run()">
    <h1>Pointer Event: Boundary compatibility events for multiple primary pointers</h1>
    <h4>
      When more than one primary pointers are active, each will have an independent sequence of pointer boundary events but the compatibilty mouse boundary events have their own sequence.
    </h4>
    Instruction:
    <ol>
      <li>Move the mouse directly into Target0 (without going through Target1), and then leave the mouse there unmoved.</li>
      <li>Tap directly on Target1 with a finger or a stylus, and then lift the finger/stylus off the screen/digitizer without crossing Target1 boundary.</li>
      <li>Move the mouse into Target0 (if not there already) and move inside it.</li>
      <li>Click Done (without passing over Target1).</li>
    </ol>
    <div id="done">
      Done
    </div>
    <div id="target0">
      Target0
    </div>
    <div id="target1">
      Target1
    </div>
    <div id="complete-notice">
      <p>The following pointer types were detected: <span id="pointertype-log"></span>.</p>
      <p>The following events were logged: <span id="event-log"></span>.</p>
    </div>
    <div id="log"></div>
  </body>
</html>
