1 /* ***************************************************************************
2 * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
19 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
20 * DEALINGS IN THE SOFTWARE.
21 * ***************************************************************************
23 * Author: Minkyu Kang <mk7.kang@samsung.com>
31 * data-role: set to 'imageslider'
32 * data-index: start index
33 * data-vertical-align: set to top or middle or bottom.
37 * add(file): add the image (parameter: url of iamge)
38 * remove(index): remove the image (parameter: index of image)
39 * refresh(index): refresh the widget, should be called after add or remove. (parameter: start index)
47 * <div data-role="imageslider" id="imageslider" data-index="3" data-vertical-align="middle">
56 * $('#imageslider-add').bind('vmouseup', function ( e ) {
57 * $('#imageslider').imageslider('add', '9.jpg');
58 * $('#imageslider').imageslider('add', '10.jpg');
59 * $('#imageslider').imageslider('refresh');
62 * $('#imageslider-del').bind('vmouseup', function ( e ) {
63 * $('#imageslider').imageslider('remove');
70 The image slider widget shows images in a gallery on the screen. <br/><br/> To add an image slider widget to the application, use the following code:
72 <div data-role="imageslider" id="imageslider" data-vertical-align="middle" data-index="3">
81 @property {Integer} data-index
82 Defines the index number of the first image in the gallery.
83 <br/>The default value is 0.
86 @property {String} data-vertical-align
87 Defines the image alignment. The alignment options are top, middle, and bottom.
88 <br/>The default value is top.
92 The add method is used to add an image to the image slider. The image_file attribute defines the image file URL.
94 <div id="imageslider" data-role="imageslider" data-vertical-align="middle"></div>
95 $("#imageslider").imageslider('add', [image_file]);
99 The del method is used to delete an image from the image slider. The image_index attribute defines the index of the image to be deleted.
101 <div id="imageslider" data-role="imageslider" data-vertical-align="middle"></div>
102 $("#imageslider").imageslider('del', [image_index]);
106 The refresh method is used to refresh the image slider. This method must be called after adding images to the image slider.
108 <div id="imageslider" data-role="imageslider" data-vertical-align="middle"></div>
109 $("#imageslider").imageslider('refresh');
111 (function ( $, window, undefined ) {
112 $.widget( "tizen.imageslider", $.mobile.widget, {
135 _resize: function ( index ) {
136 var img = this.images[index],
137 width = this.images[index].width(),
138 height = this.images[index].height(),
141 img_max_width = this.max_width - margin,
142 img_max_height = this.max_height - margin;
144 ratio = height / width;
146 if ( width > img_max_width ) {
147 img.width( img_max_width );
148 img.height( img_max_width * ratio );
151 height = img.height();
153 if ( height > img_max_height ) {
154 img.height( img_max_height );
155 img.width( img_max_height / ratio );
159 _align: function ( index, obj ) {
160 var img = this.images[index],
170 if ( this.align_type == "middle" ) {
171 img_top = ( this.max_height - img.height() ) / 2;
172 } else if ( this.align_type == "bottom" ) {
173 img_top = this.max_height - img.height();
178 obj.css( 'top', img_top + 'px' );
181 _attach: function ( index, obj ) {
183 processing = function () {
184 self._resize( index );
185 self._align( index, obj );
197 if ( index >= this.images.length ) {
201 obj.css( "display", "block" );
202 obj.append( this.images[index] );
204 if ( this.images[index].height() ) {
207 this.loader[index] = setInterval( function () {
208 if ( !self.images[index].height() ) {
213 clearInterval( self.loader[index] );
218 _detach: function ( index, obj ) {
228 if ( index >= this.images.length ) {
232 obj.css( "display", "none" );
233 this.images[index].removeAttr("style");
234 this.images[index].detach();
236 clearInterval( this.loader[index] );
239 _drag: function ( _x ) {
243 if ( !this.dragging ) {
247 if ( this.options.flicking === false ) {
248 delta = this.org_x - _x;
251 if ( delta < 0 && !this.prev_img.length ) {
255 if ( delta > 0 && !this.next_img.length ) {
260 coord_x = _x - this.org_x;
262 this.cur_img.css( 'left', coord_x + 'px' );
263 if ( this.next_img.length ) {
264 this.next_img.css( 'left', coord_x + this.window_width + 'px' );
266 if ( this.prev_img.length ) {
267 this.prev_img.css( 'left', coord_x - this.window_width + 'px' );
271 _move: function ( _x ) {
272 var delta = this.org_x - _x,
283 flip = delta < ( this.max_width * 0.45 ) ? 0 : 1;
285 flip = -delta < ( this.max_width * 0.45 ) ? 0 : 1;
289 drag_time = Date.now() - this.org_time;
291 if ( Math.abs( delta ) / drag_time > 1 ) {
297 if ( delta > 0 && this.next_img.length ) {
299 this._detach( this.index - 1, this.prev_img );
301 this.prev_img = this.cur_img;
302 this.cur_img = this.next_img;
303 this.next_img = this.next_img.next();
307 if ( this.next_img.length ) {
308 this.next_img.css( 'left', this.window_width + 'px' );
309 this._attach( this.index + 1, this.next_img );
314 } else if ( delta < 0 && this.prev_img.length ) {
316 this._detach( this.index + 1, this.next_img );
318 this.next_img = this.cur_img;
319 this.cur_img = this.prev_img;
320 this.prev_img = this.prev_img.prev();
324 if ( this.prev_img.length ) {
325 this.prev_img.css( 'left', -this.window_width + 'px' );
326 this._attach( this.index - 1, this.prev_img );
333 sec = this.options.duration;
338 setTimeout( function () {
342 this.cur_img.animate( { left: 0 }, sec );
343 if ( this.next_img.length ) {
344 this.next_img.animate( { left: this.window_width }, sec );
346 if ( this.prev_img.length ) {
347 this.prev_img.animate( { left: -this.window_width }, sec );
351 _add_event: function () {
355 this.container.bind( 'vmousemove', function ( e ) {
361 if ( !self.dragging ) {
365 self._drag( e.pageX );
368 this.container.bind( 'vmousedown', function ( e ) {
375 self.dragging = true;
377 self.org_x = e.pageX;
379 self.org_time = Date.now();
382 this.container.bind( 'vmouseup', function ( e ) {
387 self.dragging = false;
389 self._move( e.pageX );
392 this.container.bind( 'vmouseout', function ( e ) {
396 if ( !self.dragging ) {
400 if ( ( e.pageX < 20 ) ||
401 ( e.pageX > ( self.max_width - 20 ) ) ) {
402 self._move( e.pageX );
403 self.dragging = false;
408 _del_event: function () {
409 this.container.unbind( 'vmousemove' );
410 this.container.unbind( 'vmousedown' );
411 this.container.unbind( 'vmouseup' );
412 this.container.unbind( 'vmouseout' );
417 this.window_width = $( window ).width();
418 this.max_width = this._get_width();
419 this.max_height = this._get_height();
420 this.container.css( 'height', this.max_height );
422 this.cur_img = $( 'div' ).find( '.ui-imageslider-bg:eq(' + this.index + ')' );
423 this.prev_img = this.cur_img.prev();
424 this.next_img = this.cur_img.next();
426 this._attach( this.index - 1, this.prev_img );
427 this._attach( this.index, this.cur_img );
428 this._attach( this.index + 1, this.next_img );
430 if ( this.prev_img.length ) {
431 this.prev_img.css( 'left', -this.window_width + 'px' );
434 this.cur_img.css( 'left', '0px' );
436 if ( this.next_img.length ) {
437 this.next_img.css( 'left', this.window_width + 'px' );
447 this._detach( this.index - 1, this.prev_img );
448 this._detach( this.index, this.cur_img );
449 this._detach( this.index + 1, this.next_img );
457 _get_width: function () {
458 var $page = $( this.element ).parentsUntil( 'ui-page' ),
459 $content = $page.children( '.ui-content' ),
460 padding = parseFloat( $content.css( 'padding-left' ) )
461 + parseFloat( $content.css( 'padding-right' ) ),
462 content_w = $( window ).width() - padding;
467 _get_height: function () {
468 var $page = $( this.element ).parentsUntil( 'ui-page' ),
469 $content = $page.children( '.ui-content' ),
470 header_h = $page.children( '.ui-header' ).outerHeight() || 0,
471 footer_h = $page.children( '.ui-footer' ).outerHeight() || 0,
472 padding = parseFloat( $content.css( 'padding-top' ) )
473 + parseFloat( $content.css( 'padding-bottom' ) ),
474 content_h = $( window ).height() - header_h - footer_h - padding;
479 _create: function () {
485 $( this.element ).wrapInner( '<div class="ui-imageslider"></div>' );
486 $( this.element ).find( 'img' ).wrap( '<div class="ui-imageslider-bg"></div>' );
488 this.container = $( this.element ).find('.ui-imageslider');
490 temp_img = $( 'div' ).find( '.ui-imageslider-bg:first' );
492 while ( temp_img.length ) {
493 this.images[i] = temp_img.find( 'img' );
494 temp_img = temp_img.next();
498 for ( i = 0; i < this.images.length; i++ ) {
499 this.images[i].detach();
502 index = parseInt( $( this.element ).jqmData( 'index' ), 10 );
509 if ( index >= this.images.length ) {
510 index = this.images.length - 1;
515 this.align_type = $( this.element ).jqmData( 'vertical-align' );
517 $( window ).bind( 'resize', function () {
522 _update: function () {
527 while ( this.images_hold.length ) {
528 image_file = this.images_hold.shift();
530 bg_html = $( '<div class="ui-imageslider-bg"></div>' );
531 temp_img = $( '<img src="' + image_file + '"></div>' );
533 bg_html.append( temp_img );
534 this.container.append( bg_html );
535 this.images.push( temp_img );
539 refresh: function ( start_index ) {
544 if ( start_index === undefined ) {
545 start_index = this.index;
547 if ( start_index < 0 ) {
550 if ( start_index >= this.images.length ) {
551 start_index = this.images.length - 1;
554 this.index = start_index;
559 add: function ( file ) {
560 this.images_hold.push( file );
563 remove: function ( index ) {
566 if ( index === undefined ) {
570 if ( index < 0 || index >= this.images.length ) {
574 if ( index == this.index ) {
575 temp_img = this.cur_img;
577 if ( this.index == 0 ) {
579 } else if ( this.index == this.images.length - 1 ) {
583 if ( this.direction < 0 ) {
584 this.cur_img = this.prev_img;
585 this.prev_img = this.prev_img.prev();
586 if ( this.prev_img.length ) {
587 this.prev_img.css( 'left', -this.window_width );
588 this._attach( index - 2, this.prev_img );
592 this.cur_img = this.next_img;
593 this.next_img = this.next_img.next();
594 if ( this.next_img.length ) {
595 this.next_img.css( 'left', this.window_width );
596 this._attach( index + 2, this.next_img );
600 this.cur_img.animate( { left: 0 }, this.options.duration );
602 } else if ( index == this.index - 1 ) {
603 temp_img = this.prev_img;
604 this.prev_img = this.prev_img.prev();
605 if ( this.prev_img.length ) {
606 this.prev_img.css( 'left', -this.window_width );
607 this._attach( index - 1, this.prev_img );
611 } else if ( index == this.index + 1 ) {
612 temp_img = this.next_img;
613 this.next_img = this.next_img.next();
614 if ( this.next_img.length ) {
615 this.next_img.css( 'left', this.window_width );
616 this._attach( index + 1, this.next_img );
620 temp_img = $( 'div' ).find( '.ui-imageslider-bg:eq(' + index + ')' );
623 this.images.splice( index, 1 );
626 }); /* End of widget */
628 // auto self-init widgets
629 $( document ).bind( "pagecreate", function ( e ) {
630 $( e.target ).find( ":jqmData(role='imageslider')" ).imageslider();
633 $( document ).bind( "pageshow", function ( e ) {
634 $( e.target ).find( ":jqmData(role='imageslider')" ).imageslider( 'show' );
637 $( document ).bind( "pagebeforehide", function ( e ) {
638 $( e.target ).find( ":jqmData(role='imageslider')" ).imageslider( 'hide' );