|
9 | 9 |
|
10 | 10 | {{index stoicism, "Marcus Aurelius", input, timeline, "control flow"}} |
11 | 11 |
|
12 | | -// FIXME mention touch event handling |
13 | | - |
14 | 12 | Some programs work with direct user input, such as mouse and keyboard. |
15 | 13 | That kind of input isn't available as a whole at the start of your |
16 | 14 | program—it comes in piece by piece, and the program is expected to |
@@ -367,9 +365,16 @@ To notice when something was typed, elements that you can type into, |
367 | 365 | such as the `<input>` and `<textarea>` tags, fire `"input"` events |
368 | 366 | whenever the user changed their content. To get the actual content |
369 | 367 | that was typed, it is best to directly read it from the page. [Chapter |
370 | | -?](forms) will show how. |
| 368 | +?](http#forms) will show how. |
| 369 | + |
| 370 | +## Pointer events |
| 371 | + |
| 372 | +There are currently two widely used ways to point at things on a |
| 373 | +screen: mice (including devices that act like mice, such as touchpads |
| 374 | +and trackballs) and touchscreens. These produce different kinds of |
| 375 | +events. |
371 | 376 |
|
372 | | -## Mouse clicks |
| 377 | +### Mouse clicks |
373 | 378 |
|
374 | 379 | {{index "mousedown event", "mouseup event", "mouse cursor"}} |
375 | 380 |
|
@@ -433,7 +438,7 @@ click the document, it adds a dot under your mouse pointer. See |
433 | 438 | </script> |
434 | 439 | ``` |
435 | 440 |
|
436 | | -## Mouse motion |
| 441 | +### Mouse motion |
437 | 442 |
|
438 | 443 | {{index "mousemove event"}} |
439 | 444 |
|
@@ -504,6 +509,72 @@ one used by `button`, where the middle button came before the right |
504 | 509 | one. As mentioned, consistency isn't really a strong point of the |
505 | 510 | browser's programming interface. |
506 | 511 |
|
| 512 | +### Touch events |
| 513 | + |
| 514 | +{{index touch, "mousedown event", "mouseup event", "click event"}} |
| 515 | + |
| 516 | +The style of graphical browser that we use was designed with mouse |
| 517 | +interfaces in mind, at a time where touchscreens were very rare. To |
| 518 | +make the Web "work" on early touchscreen phones, browsers for those |
| 519 | +devices pretended, to a certain extent, that touch events were mouse |
| 520 | +events. If you tap your screen, you'll get `"mousedown"`, `"mouseup"`, |
| 521 | +and `"click"` events. |
| 522 | + |
| 523 | +But this illusion isn't very robust. A touchscreen works differently |
| 524 | +from a mouse: it doesn't have multiple buttons, you can't track the |
| 525 | +finger when it isn't on the screen (to simulate `"mousemove"`), and it |
| 526 | +allows multiple fingers to be on the screen at the same time. |
| 527 | + |
| 528 | +Mouse events only cover touch interaction in straightforward cases—if |
| 529 | +you add a `"click"` handler to a button, touch users will still be |
| 530 | +able to use it. But something like the resizeable bar in the last |
| 531 | +example does not work on a touchscreen. |
| 532 | + |
| 533 | +{{index "touchstart event", "touchmove event", "touchend event"}} |
| 534 | + |
| 535 | +There are separate event types fired by touch interaction. When a |
| 536 | +finger starts touching the screen, you get a `"touchstart"` event. |
| 537 | +When it is moved while touching, `"touchmove"` events fire. And |
| 538 | +finally, when it stops touching the screen, you'll see a `"touchend"` |
| 539 | +event. |
| 540 | + |
| 541 | +{{index "touches property", "clientX property", "clientY property", "pageX property", "pageY property"}} |
| 542 | + |
| 543 | +Because many touchscreens can detect multiple fingers at the same |
| 544 | +time, these events don't have a single set of coordinates associated |
| 545 | +with them. Rather, their ((event object))s have a `touches` property, |
| 546 | +which holds an ((array-like object)) of points, each of which has its |
| 547 | +own `clientX`, `clientY`, `pageX`, and `pageY` properties. |
| 548 | + |
| 549 | +You could do something like this to show red circles around every |
| 550 | +touching finger. |
| 551 | + |
| 552 | +```{lang: "text/html"} |
| 553 | +<style> |
| 554 | + dot { position: absolute; display: block; |
| 555 | + border: 2px solid red; border-radius: 50px; |
| 556 | + height: 100px; width: 100px; } |
| 557 | +</style> |
| 558 | +<p>Touch this page</p> |
| 559 | +<script> |
| 560 | + function update(event) { |
| 561 | + for (let dot; dot = document.querySelector("dot");) { |
| 562 | + dot.remove(); |
| 563 | + } |
| 564 | + for (let i = 0; i < event.touches.length; i++) { |
| 565 | + let {pageX, pageY} = event.touches[i]; |
| 566 | + let dot = document.createElement("dot"); |
| 567 | + dot.style.left = (pageX - 50) + "px"; |
| 568 | + dot.style.top = (pageY - 50) + "px"; |
| 569 | + document.body.appendChild(dot); |
| 570 | + } |
| 571 | + } |
| 572 | + addEventListener("touchstart", update); |
| 573 | + addEventListener("touchmove", update); |
| 574 | + addEventListener("touchend", update); |
| 575 | +</script> |
| 576 | +``` |
| 577 | + |
507 | 578 | ## Scroll events |
508 | 579 |
|
509 | 580 | {{index scrolling, "scroll event", "event handling"}} |
|
0 commit comments