~bac/juju-gui/trunkcopy

« back to all changes in this revision

Viewing changes to lib/yui/docs/event/swipe-example.html

  • Committer: kapil.foss at gmail
  • Date: 2012-07-13 18:45:59 UTC
  • Revision ID: kapil.foss@gmail.com-20120713184559-2xl7be17egsrz0c9
reshape

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
<!DOCTYPE html>
2
 
<html lang="en">
3
 
<head>
4
 
    <meta charset="utf-8">
5
 
    <title>Example: Supporting A Swipe Left Gesture</title>
6
 
    <link rel="stylesheet" href="http://fonts.googleapis.com/css?family=Maven+Pro:400,700">
7
 
    <link rel="stylesheet" href="../../build/cssgrids/grids-min.css">
8
 
    <link rel="stylesheet" href="../assets/css/main.css">
9
 
    <link rel="stylesheet" href="../assets/vendor/prettify/prettify-min.css">
10
 
    <script src="../../build/yui/yui-min.js"></script>
11
 
</head>
12
 
<body>
13
 
 
14
 
<div id="doc">
15
 
    <h1>Example: Supporting A Swipe Left Gesture</h1>
16
 
 
17
 
    
18
 
 
19
 
    <div class="yui3-g">
20
 
        <div class="yui3-u-3-4">
21
 
            <div id="main">
22
 
                <div class="content"><div class="intro">
23
 
    <p>
24
 
        This example shows how you can support a "swipeleft" gesture, built on
25
 
        top of the synthetic "gesturemove" events, which work not only on touch
26
 
        devices, but also on mouse based input devices.
27
 
    </p>
28
 
</div>
29
 
 
30
 
<div class="example newwindow">
31
 
    <a href="swipe-example-content.html" target="_blank" class="button">
32
 
        View Example in New Window
33
 
    </a>
34
 
</div>
35
 
 
36
 
<h2>Modules Used</h2>
37
 
 
38
 
<p>For the example, the two core modules we'll use are:</p>
39
 
 
40
 
<dl>
41
 
    <dt>The <code>event-move</code> module</dt> 
42
 
    <dd>
43
 
        Provides the <code>gesturemovestart</code>, <code>gesturemove</code> and <code>gesturemoveend</code>
44
 
        low-level gesture events. These events are fired whenever the user
45
 
        performs a move gesture (mouse button/finger down, mouse/finger move,
46
 
        mouse button/finger up) with the mouse or their finger.
47
 
    </dd>
48
 
    <dt>The <code>transitions</code> module</dt>
49
 
    <dd>
50
 
        Provides transitions support, leveraging CSS transitions under the hood
51
 
        where supported.
52
 
    </dd>
53
 
</dl>
54
 
 
55
 
<p>The YUI use statement for the example is shown below:</p>
56
 
 
57
 
<pre class="code prettyprint">YUI().use(&quot;node-base&quot;, &quot;node-event-delegate&quot;, &quot;transition&quot;, &quot;event-move&quot;, function(Y) {
58
 
    ...
59
 
});</pre>
60
 
 
61
 
 
62
 
<h2>Delegating Gesture Move Events</h2>
63
 
 
64
 
<p>
65
 
    The basic idea for the example is to listen for a <code>gesturemovestart</code> on a
66
 
    list item, and when we get one, store its position, and then listen for a
67
 
    gesturemoveend. If the gesturemoveend occurs more than X pixels to the left
68
 
    of the start, then we've identified a "swipeleft" gesture. Future versions
69
 
    of the library will package such logic into a higher level gesture event
70
 
    (ala event-flick).
71
 
</p>
72
 
 
73
 
<p>
74
 
    For this example, since we're dealing with a list of items, rather than
75
 
    attach individual listeners to each &#60;li&#62; in the list, we use
76
 
    <code>delegate</code> on the parent &#60;ul&#62; element, which leads to better
77
 
    performance and avoids having to add/remove listeners each time the
78
 
    contents of the list change.  The <code>gesturemovestart</code>, <code>gesturemove</code> and
79
 
    <code>gesturemoveend</code> are synthetic events, and can all be used with <code>delegate</code>,
80
 
    just like any DOM event. 
81
 
</p>
82
 
 
83
 
<p>
84
 
    We set up a delegate listener on the &#60;ul&#62; which listens for the
85
 
    <code>gesturemovestart</code> event (<code>gesturemovestart</code> abstracts
86
 
    <code>mousedown</code>/<code>touchstart</code> events under the hood). The delegate listener is
87
 
    set up to be notified when the target of the <code>gesturemovestart</code> is an
88
 
    <code>&lt;li&gt;</code>
89
 
</p>
90
 
 
91
 
<pre class="code prettyprint">Y.Node.one(&quot;#swipe&quot;).delegate(&quot;gesturemovestart&quot;, function(e) {
92
 
 
93
 
    ...
94
 
 
95
 
}, &quot;li&quot;, {  &#x2F;&#x2F; filter for &quot;li&quot;
96
 
    preventDefault:true
97
 
});</pre>
98
 
 
99
 
 
100
 
<p>
101
 
    The <code>gesturemovestart</code> event supports a configuration object passed as an
102
 
    additional subscription argument, which can be used to set minimum distance
103
 
    and minimum time thresholds at which to fire the start event. The
104
 
    configuration also supports the ability to prevent the default behavior
105
 
    before the minimum time or distance thresholds kick in, which is what we do
106
 
    above by passing <code>preventDefault:true</code>.
107
 
</p>
108
 
 
109
 
<p>
110
 
    The advantage of the gesture synthetic events is that the developer can use
111
 
    the same API without having to worry about whether or not the browser
112
 
    platform is touch based or mouse based.
113
 
</p>
114
 
 
115
 
<h2>Gesture Move End</h2>
116
 
 
117
 
<p>
118
 
    As mentioned above, the <code>gesturemovestart</code> listener is notified whenever a
119
 
    <code>mousedown</code> or <code>touchstart</code> is received on a list item. The listener has
120
 
    access to:
121
 
</p>
122
 
 
123
 
<dl>
124
 
    <dt><code>e.currentTarget</code></dt>
125
 
        <dd>The list item targeted.</dd>
126
 
    <dt><code>e.target</code></dt>
127
 
        <dd>
128
 
            The element clicked on (it may be an element inside the targeted
129
 
            list item, the span for example).
130
 
        </dd>
131
 
    <dt><code>e.container</code></dt>
132
 
        <dd>
133
 
            The element to which the delegate listener is attached (the ul in
134
 
            this case).
135
 
        </dd>
136
 
</dl>
137
 
 
138
 
<p>
139
 
    The event facade also has the page coordinates for the <code>mousedown</code> or
140
 
    <code>touchstart</code> event. We use the list item's <code>setData</code> method, to store the
141
 
    <code>pageX</code> position for the start event, so we can compare it when we get the
142
 
    <code>gesturemoveend</code> event. This way it's stored on the node instance, and we
143
 
    don't need to pass it along separately to the <code>gesturemoveend</code> event, or
144
 
    store it globally.
145
 
</p> 
146
 
 
147
 
<p>
148
 
    <code>getData</code>, <code>setData</code> and <code>clearData</code> are useful methods to store ad-hoc
149
 
    node centric data.
150
 
</p>
151
 
 
152
 
<pre class="code prettyprint">Y.Node.one(&quot;#swipe&quot;).delegate(&quot;gesturemovestart&quot;, function(e) {
153
 
 
154
 
    var item = e.currentTarget,
155
 
        target = e.target,
156
 
        container = e.container,
157
 
 
158
 
    ...
159
 
 
160
 
    item.setData(&quot;swipeStart&quot;, e.pageX);
161
 
 
162
 
    item.once(&quot;gesturemoveend&quot;, function(e) {
163
 
 
164
 
        var swipeStart = item.getData(&quot;swipeStart&quot;),
165
 
            swipeEnd = e.pageX,
166
 
            isSwipeLeft = (swipeStart - swipeEnd) &gt; MIN_SWIPE;
167
 
 
168
 
        if (isSwipeLeft) {
169
 
            item.one(&quot;.myapp-delete&quot;).removeClass(&quot;myapp-hidden&quot;);
170
 
        }
171
 
 
172
 
    });
173
 
 
174
 
    ...
175
 
 
176
 
});</pre>
177
 
 
178
 
 
179
 
<p>
180
 
    When we get the <code>gesturemovestart</code> event, we set up a listener for the
181
 
    <code>gesturemoveend</code> event, so we can determine the end of the gesture, and
182
 
    figure out if the user swiped left. Since we don't want to set up a new
183
 
    listener every time we get a <code>gesturemovestart</code> we use <code>once</code> to set up the
184
 
    <code>gesturemoveend</code> listener. <code>once</code> will detach the listener after it's been
185
 
    invoked. Again, since <code>gesturemoveend</code> is a synthetic event, it works with
186
 
    <code>once</code> just like any other DOM event.
187
 
</p>
188
 
 
189
 
<p>
190
 
    In the <code>gesturemoveend</code> listener we check the page position of the event,
191
 
    and if it's far enough to the left of the start position, we display the
192
 
    "Delete" button by removing the hidden class which it contains.
193
 
</p>
194
 
 
195
 
<h2>Transitions</h2>
196
 
 
197
 
<p>
198
 
    To hide and remove the item when the delete button is pressed, we use the
199
 
    <code>transition</code> method, to animate its opacity and height down to 0. Under the
200
 
    hood transition will use CSS transition support where available (WebKit)
201
 
    and set up timer based animation where not (IE). As with the gesture event
202
 
    support, the developer gets to use the same API without having to worry
203
 
    about the browser environment.
204
 
</p>
205
 
 
206
 
<pre class="code prettyprint">item = target.get(&quot;parentNode&quot;);
207
 
 
208
 
item.transition({
209
 
    duration:0.3,
210
 
    opacity:0,
211
 
    height:0
212
 
}, function() {
213
 
    this.remove();
214
 
});</pre>
215
 
 
216
 
 
217
 
<p>
218
 
    The second argument to transition above is a callback function, which is
219
 
    invoked when the transition is complete. We use this support to remove the
220
 
    item from the DOM.
221
 
</p>
222
 
 
223
 
<h2>Full Code Listing</h2>
224
 
 
225
 
<pre class="code prettyprint">YUI().use(&#x27;node-base&#x27;,&#x27;node-event-delegate&#x27;, &#x27;transition&#x27;, &#x27;event-move&#x27;, function (Y) {
226
 
 
227
 
    var MIN_SWIPE = 10;
228
 
 
229
 
    Y.all(&quot;.myexample-hidden&quot;).removeClass(&quot;myexample-hidden&quot;);
230
 
 
231
 
    Y.one(&quot;#swipe&quot;).delegate(&quot;gesturemovestart&quot;, function(e) {
232
 
 
233
 
        var item = e.currentTarget,
234
 
            target = e.target,
235
 
            container = e.container,
236
 
            isDeleteButton = target.hasClass(&quot;myapp-delete&quot;);
237
 
 
238
 
        &#x2F;&#x2F; Prevent Text Selection in IE
239
 
        item.once(&quot;selectstart&quot;, function(e) {
240
 
            e.preventDefault();
241
 
        });
242
 
 
243
 
        if (!isDeleteButton) {
244
 
 
245
 
            container.all(&quot;.myapp-delete&quot;).addClass(&quot;myapp-hidden&quot;);
246
 
 
247
 
            item.setData(&quot;swipeStart&quot;, e.pageX);
248
 
 
249
 
            item.once(&quot;gesturemoveend&quot;, function(e) {
250
 
 
251
 
                var swipeStart = item.getData(&quot;swipeStart&quot;),
252
 
                    swipeEnd = e.pageX,
253
 
                    isSwipeLeft = (swipeStart - swipeEnd) &gt; MIN_SWIPE;
254
 
 
255
 
                if (isSwipeLeft) {
256
 
                    item.one(&quot;.myapp-delete&quot;).removeClass(&quot;myapp-hidden&quot;);    
257
 
                }
258
 
 
259
 
            });
260
 
        } else {
261
 
            item = target.get(&quot;parentNode&quot;);
262
 
 
263
 
            if (item.get(&quot;id&quot;) != &quot;kitkat&quot; || confirm(&quot;Seriously? The KitKats?&quot;)) {
264
 
                item.transition({
265
 
                    duration:0.3,
266
 
                    opacity:0,
267
 
                    height:0
268
 
                }, function() {
269
 
                    this.remove();
270
 
                });
271
 
            }
272
 
        }
273
 
 
274
 
    }, &quot;li&quot;, {
275
 
        preventDefault:true
276
 
    });
277
 
});</pre>
278
 
 
279
 
</div>
280
 
            </div>
281
 
        </div>
282
 
 
283
 
        <div class="yui3-u-1-4">
284
 
            <div class="sidebar">
285
 
                
286
 
 
287
 
                
288
 
                    <div class="sidebox">
289
 
                        <div class="hd">
290
 
                            <h2 class="no-toc">Examples</h2>
291
 
                        </div>
292
 
 
293
 
                        <div class="bd">
294
 
                            <ul class="examples">
295
 
                                
296
 
                                    
297
 
                                        <li data-description="Use the Event Utility to attach simple DOM event handlers.">
298
 
                                            <a href="basic-example.html">Simple DOM Events</a>
299
 
                                        </li>
300
 
                                    
301
 
                                
302
 
                                    
303
 
                                        <li data-description="Using the synthetic event API to create a DOM event that fires in response to arrow keys being pressed.">
304
 
                                            <a href="synth-example.html">Creating an Arrow Event for DOM Subscription</a>
305
 
                                        </li>
306
 
                                    
307
 
                                
308
 
                                    
309
 
                                        <li data-description="Supporting cross-device swipe gestures, using the event-move gesture events">
310
 
                                            <a href="swipe-example.html">Supporting A Swipe Left Gesture</a>
311
 
                                        </li>
312
 
                                    
313
 
                                
314
 
                                    
315
 
                                
316
 
                                    
317
 
                                
318
 
                                    
319
 
                                
320
 
                                    
321
 
                                
322
 
                                    
323
 
                                
324
 
                            </ul>
325
 
                        </div>
326
 
                    </div>
327
 
                
328
 
 
329
 
                
330
 
                    <div class="sidebox">
331
 
                        <div class="hd">
332
 
                            <h2 class="no-toc">Examples That Use This Component</h2>
333
 
                        </div>
334
 
 
335
 
                        <div class="bd">
336
 
                            <ul class="examples">
337
 
                                
338
 
                                    
339
 
                                
340
 
                                    
341
 
                                
342
 
                                    
343
 
                                
344
 
                                    
345
 
                                        <li data-description="Shows how to extend the base widget class, to create your own Widgets.">
346
 
                                            <a href="../widget/widget-extend.html">Extending the Base Widget Class</a>
347
 
                                        </li>
348
 
                                    
349
 
                                
350
 
                                    
351
 
                                        <li data-description="Creating an accessible menu button using the Focus Manager Node Plugin, Event&#x27;s delegation support and mouseenter event, along with the Overlay widget and Node&#x27;s support for the WAI-ARIA Roles and States.">
352
 
                                            <a href="../node-focusmanager/node-focusmanager-3.html">Accessible Menu Button</a>
353
 
                                        </li>
354
 
                                    
355
 
                                
356
 
                                    
357
 
                                        <li data-description="Use IO to request data over HTTP.">
358
 
                                            <a href="../io/get.html">HTTP GET to request data</a>
359
 
                                        </li>
360
 
                                    
361
 
                                
362
 
                                    
363
 
                                        <li data-description="Example Photo Browser application.">
364
 
                                            <a href="../dd/photo-browser.html">Photo Browser</a>
365
 
                                        </li>
366
 
                                    
367
 
                                
368
 
                                    
369
 
                                        <li data-description="Portal style example using Drag &amp; Drop Event Bubbling and Animation.">
370
 
                                            <a href="../dd/portal-drag.html">Portal Style Example</a>
371
 
                                        </li>
372
 
                                    
373
 
                                
374
 
                            </ul>
375
 
                        </div>
376
 
                    </div>
377
 
                
378
 
            </div>
379
 
        </div>
380
 
    </div>
381
 
</div>
382
 
 
383
 
<script src="../assets/vendor/prettify/prettify-min.js"></script>
384
 
<script>prettyPrint();</script>
385
 
 
386
 
</body>
387
 
</html>