2 * jQuery Mobile Widget @VERSION
4 * This software is licensed under the MIT licence (as defined by the OSI at
5 * http://www.opensource.org/licenses/mit-license.php)
7 * ***************************************************************************
8 * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
9 * Copyright (c) 2011 by Intel Corporation Ltd.
11 * Permission is hereby granted, free of charge, to any person obtaining a
12 * copy of this software and associated documentation files (the "Software"),
13 * to deal in the Software without restriction, including without limitation
14 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
15 * and/or sell copies of the Software, and to permit persons to whom the
16 * Software is furnished to do so, subject to the following conditions:
18 * The above copyright notice and this permission notice shall be included in
19 * all copies or substantial portions of the Software.
21 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
22 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
23 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
24 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
25 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
26 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
27 * DEALINGS IN THE SOFTWARE.
28 * ***************************************************************************
30 * Authors: Kalyan Kondapally <kalyan.kondapally@intel.com>,
31 * Elliot Smith <elliot.smith@intel.com>
34 // Widget which turns a list into a "swipe list":
35 // i.e. each list item has a sliding "cover" which can be swiped
36 // to the right (to reveal buttons underneath) or left (to
37 // cover the buttons again). Clicking on a button under a swipelist
38 // also moves the cover back to the left.
40 // To create a swipelist, you need markup like this:
43 // <ul data-role="swipelist"><br/>
45 // <div class="ui-grid-b"><br/>
46 // <div class="ui-block-a"><br/>
47 // <a href="#" data-role="button" data-theme="a">Twitter</a><br/>
49 // <div class="ui-block-b"><br/>
50 // <a href="#" data-role="button" data-theme="b">FaceBook</a><br/>
52 // <div class="ui-block-c"><br/>
53 // <a href="#" data-role="button" data-theme="c">Google+</a><br/>
56 // <div data-role="swipelist-item-cover">Nigel</div><br/>
62 // In this case, the cover is over a grid of buttons;
63 // but it is should also be possible to use other types of markup under the
66 // Note the use of a separate div, parented by the li element, marked
67 // up with data-role="swipelist-item-cover". This div will usually
68 // contain text. If you want other elements in your swipelist covers,
69 // you may need to style them yourself. Because the covers aren't
70 // technically list items, you may need to do some work to make them
73 // WARNING: This doesn't work well inside a scrollview widget, as
74 // the touch events currently interfere with each other badly (e.g.
75 // a swipe will work but cause a scroll as well).
77 // Theme: default is to use the theme on the target element,
78 // theme passed in options, parent theme, or 'c' if none of the above.
79 // If list items are themed individually, the cover will pick up the
80 // theme of the list item which is its parent.
84 // animationComplete: Triggered by a cover when it finishes sliding
85 // (to either the right or left).
89 The swipe list widget shows a list view on the screen where the list items can be swiped vertically to show a menu.
90 To add a swipe list widget to the application, use the following code:
92 <ul data-role="swipelist">
94 <div data-role="button" data-inline="true">OK</div>
95 <div data-role="button" data-inline="true">Cancel</div>
96 <div data-role="swipelist-item-cover">
97 <p>This is a swipelist item cover.<br>
98 This will be swiped out when swipe event comes.</p>
103 You can use methods with the swipe list as described in the jQueryMobile documentation for list view methods.
106 @property {String} data-role
107 Creates a swipe list using the HTML unordered list (>ul<) element.
108 The default value is swipelist.
110 Creates a swipe list item cover using an HTML $gt;div$lt; element. This cover can be swiped to show the content beneath it.
111 The default value is swipelist-item-cover.
115 The swipe list can define a callback for the animationend event, which is fired after a list item is swiped and the swipe animation is complete:
117 <ul data-role="swipelist">
119 <div data-role="button" data-inline="true">OK</div>
120 <div data-role="button" data-inline="true">Cancel</div>
121 <div data-role="swipelist-item-cover" id="foo">
122 <p>This is a swipelist item cover.<br>
123 This will be swiped out when swipe event comes.</p>
127 $("#foo").bind("animationend", function (ev)
129 Console.log("Swipelist cover's animation is complete.");
134 $.widget("tizen.swipelist", $.mobile.widget, {
139 _create: function () {
140 // use the theme set on the element, set in options,
141 // the parent theme, or 'c' (in that order of preference)
142 var theme = this.element.jqmData('theme') ||
143 this.options.theme ||
144 this.element.parent().jqmData('theme') ||
147 this.options.theme = theme;
151 refresh: function () {
158 defaultCoverTheme = 'ui-body-' + this.options.theme;
160 // swipelist is a listview
161 if (!this.element.hasClass('ui-listview')) {
162 this.element.listview();
165 this.element.addClass('ui-swipelist');
167 // get the list item covers
168 covers = this.element.find(':jqmData(role="swipelist-item-cover")');
170 covers.each(function () {
172 coverTheme = defaultCoverTheme,
173 // get the parent li element and add classes
174 item = cover.closest('li'),
177 // add swipelist CSS classes
178 item.addClass('ui-swipelist-item');
179 cover.addClass('ui-swipelist-item-cover');
181 // set swatch on cover: if the nearest list item has
182 // a swatch set on it, that will be used; otherwise, use
183 // the swatch set for the swipelist
184 itemHasThemeClass = item.attr('class')
185 .match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/);
187 if (itemHasThemeClass) {
188 coverTheme = itemHasThemeClass[0];
191 cover.addClass(coverTheme);
193 // wrap inner HTML (so it can potentially be styled)
194 if (cover.has('.ui-swipelist-item-cover-inner').length === 0) {
195 cover.wrapInner($('<span/>').addClass('ui-swipelist-item-cover-inner'));
198 // bind to swipe events on the cover and the item
199 if (!(cover.data('animateRight') && cover.data('animateLeft'))) {
200 cover.data('animateRight', function () {
201 self._animateCover(cover, 100);
204 cover.data('animateLeft', function () {
205 self._animateCover(cover, 0);
209 // bind to synthetic events
210 item.bind('swipeleft', cover.data('animateLeft'));
211 cover.bind('swiperight', cover.data('animateRight'));
213 // any clicks on buttons inside the item also trigger
214 // the cover to slide back to the left
215 item.find('.ui-btn').bind('vclick', cover.data('animateLeft'));
219 _cleanupDom: function () {
225 defaultCoverTheme = 'ui-body-' + this.options.theme;
227 this.element.removeClass('ui-swipelist');
229 // get the list item covers
230 covers = this.element.find(':jqmData(role="swipelist-item-cover")');
232 covers.each(function () {
234 coverTheme = defaultCoverTheme,
237 // get the parent li element and add classes
238 item = cover.closest('li'),
242 // remove swipelist CSS classes
243 item.removeClass('ui-swipelist-item');
244 cover.removeClass('ui-swipelist-item-cover');
246 // remove swatch from cover: if the nearest list item has
247 // a swatch set on it, that will be used; otherwise, use
248 // the swatch set for the swipelist
249 itemClass = item.attr('class');
250 itemHasThemeClass = itemClass &&
251 itemClass.match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/);
253 if (itemHasThemeClass) {
254 coverTheme = itemHasThemeClass[0];
257 cover.removeClass(coverTheme);
259 // remove wrapper HTML
260 wrapper = cover.find('.ui-swipelist-item-cover-inner');
261 wrapper.children().unwrap();
262 text = wrapper.text();
269 // unbind swipe events
270 if (cover.data('animateRight') && cover.data('animateLeft')) {
271 cover.unbind('swiperight', cover.data('animateRight'));
272 item.unbind('swipeleft', cover.data('animateLeft'));
274 // unbind clicks on buttons inside the item
275 item.find('.ui-btn').unbind('vclick', cover.data('animateLeft'));
277 cover.data('animateRight', null);
278 cover.data('animateLeft', null);
283 // NB I tried to use CSS animations for this, but the performance
284 // and appearance was terrible on Android 2.2 browser;
285 // so I reverted to jQuery animations
287 // once the cover animation is done, the cover emits an
288 // animationComplete event
289 _animateCover: function (cover, leftPercentage) {
290 var animationOptions = {
294 complete: function () {
295 cover.trigger('animationComplete');
301 cover.animate({left: leftPercentage + '%'}, animationOptions);
304 destroy: function () {
310 $(document).bind("pagecreate", function (e) {
311 $(e.target).find(":jqmData(role='swipelist')").swipelist();