RE: Request for Comments: Pointer Events spec's touch-action CSS property

Apologies, I've corrected a mistake inline below (removed "AND that subsequent pointer events should be consumed and not dispatched" from the paragraph below the algorithm).  Any time a UA decides to perform a touch action, it must cancel the pointer. This is covered in the following spec text:

"A user agent must dispatch a pointercancel (and subsequently a pointerout event) whenever all of the following are true:
  •The user agent has determined (via methods out of scope for this specification) that touch input is to be consumed for a default touch behavior,
  •a pointerdown event has been sent for the pointer, and
  •a pointerup or pointercancel event (following the above mentioned pointerdown) has not yet been sent for the pointer.

During the execution of the behavior (after sending the pointercancel and pointerout events), the user agent must not dispatch subsequent pointer events for the pointer. "

So in other words, if events have been sent for a pointer and you later decide to perform a touch action then you must clean up state by firing pointercancel and pointerout.  UAs do not fire events while performing touch actions (panning/zooming/etc).

-----Original Message-----
From: Jacob Rossi [mailto:Jacob.Rossi@microsoft.com] 
Sent: Thursday, January 17, 2013 5:25 PM
To: L. David Baron; public-pointer-events@w3.org; Tab Atkins Jr.
Cc: www-style@w3.org
Subject: RE: Request for Comments: Pointer Events spec's touch-action CSS property

 Hey folks,

Thanks for the great feedback. I'll try to address all the questions thus far from Tab and David. But let me know if I miss something. First, I'll start with some background context on the feature.

This property is fundamentally about enabling better performance for touch panning, zooming, etc.  Performance is most critical for touch, where your finger is aligned 1:1 with the content and any lag is readily noticed by the user.

As a CSS property, the intended touch behavior is declarative and known ahead of interaction time. Whether panning/zooming should happen can be known *immediately* when the touch begins because the CSS property has a value. With preventDefault(), you have to dispatch an event first to answer that question. There could be script already running that could slow the dispatch of the event and/or script in the event handler could run for a while before returning. All the while, your finger has started to move yet  panning/zooming hasn't kicked in.  This can cause a substantial jump in the initiation of a pan, which is an undesirable touch experience. With touch-action, you know right away what to do and get a more fluid pan/zoom initiation.

The property acts as a filter on the behaviors a UA is allowed to perform. It doesn't inherit because it has its own processing model (I'll update the spec to remove "inherit" from the grammar--I didn't know the convention).  I hear the feedback that the spec text for this model is unclear. I think, perhaps, a more algorithmic approach might be better:
 
Run these steps prior to dispatching the pointerdown event for a touch:
1. Set ELEMENT to the target of the pointerdown.
2. If the value of touch-action for ELEMENT is "none" then terminate these steps.
3. If ELEMENT is capable of a performing a touch behavior (such as panning or zooming), then begin considering this touch for that possible behavior and abort these steps.
4. If ELEMENT is the root of the document, terminate these steps.
5. Set ELEMENT to the current ELEMENT's immediate parent and repeat steps 2-5.

This locates a "touch behavior capable element" that is monitoring active touches. When a UA determines a touch should trigger a behavior on this element (by methods outside the scope of this spec), then it must cancel that pointer by dispatching pointercancel and pointerout events.  It is not necessarily a requirement that all touch behaviors result in the consumption of pointer events, but if they do then they must dispatch the cancel/out.

Some basic examples:
<div style="touch-action: none;" >
     <div style="overflow:scroll;"></div> </div> A touch on the child may perform a pan on the child.
 
<div style="overflow:scroll;">
   <div style="touch-action: none;" ></div>  </div> A touch on the child must not perform a pan on the parent.

<div style="overflow:scroll; touch-action: none;"></div> A touch on the element must not perform a pan on the element.

As for the block-level restriction, this was simply an optimization we made to IE10, which the spec is based on. In general, only block-level elements are capable of these types of behaviors. As for the name, well it's the *actions* (think: default action from events) that the *touch* can perform. We'd like to shoot for interop with IE10, but we're open for suggestions on other names if there's a strong objection to the current.

 -Jacob

Received on Friday, 18 January 2013 01:39:53 UTC