/*
-* jQuery Mobile Framework : scrollview plugin
-* Copyright (c) 2010 Adobe Systems Incorporated - Kin Blas (jblas@adobe.com)
-* Dual licensed under the MIT (MIT-LICENSE.txt) and GPL (GPL-LICENSE.txt) licenses.
-* Note: Code is in draft form and is subject to change
-* Modified by Koeun Choi <koeun.choi@samsung.com>
-* Modified by Minkyu Kang <mk7.kang@samsung.com>
-*/
-
-(function ( $, window, document, undefined ) {
-
- function resizePageContentHeight( page ) {
- var $page = $( page ),
- $content = $page.children(".ui-content"),
- hh = $page.children(".ui-header").outerHeight() || 0,
- fh = $page.children(".ui-footer").outerHeight() || 0,
- pt = parseFloat( $content.css("padding-top") ),
- pb = parseFloat( $content.css("padding-bottom") ),
- wh = $( window ).height();
-
- $content.height( wh - (hh + fh) - (pt + pb) );
- }
-
- function MomentumTracker( options ) {
- this.options = $.extend( {}, options );
- this.easing = "easeOutQuad";
- this.reset();
- }
-
- var tstates = {
- scrolling: 0,
- overshot: 1,
- snapback: 2,
- done: 3
- };
-
- function getCurrentTime() {
- return Date.now();
- }
-
- jQuery.widget( "tizen.scrollview", jQuery.mobile.widget, {
- options: {
- direction: null, // "x", "y", or null for both.
-
- timerInterval: 10,
- scrollDuration: 1000, // Duration of the scrolling animation in msecs.
- overshootDuration: 250, // Duration of the overshoot animation in msecs.
- snapbackDuration: 500, // Duration of the snapback animation in msecs.
-
- moveThreshold: 30, // User must move this many pixels in any direction to trigger a scroll.
- moveIntervalThreshold: 150, // Time between mousemoves must not exceed this threshold.
-
- scrollMethod: "translate", // "translate", "position"
- startEventName: "scrollstart",
- updateEventName: "scrollupdate",
- stopEventName: "scrollstop",
-
- eventType: $.support.touch ? "touch" : "mouse",
-
- showScrollBars: true,
- overshootEnable: false,
- outerScrollEnable: false,
- overflowEnable: true,
- scrollJump: false
- },
-
- _getViewHeight: function () {
- return this._$view.height();
- },
-
- _getViewWidth: function () {
- return this._$view.width();
- },
-
- _makePositioned: function ( $ele ) {
- if ( $ele.css("position") === "static" ) {
- $ele.css( "position", "relative" );
- }
- },
-
- _create: function () {
- var direction,
- self = this;
-
- this._$clip = $( this.element ).addClass("ui-scrollview-clip");
-
- if ( this._$clip.children(".ui-scrollview-view").length ) {
- this._$view = this._$clip.children(".ui-scrollview-view");
- } else {
- this._$view = this._$clip.wrapInner("<div></div>").children()
- .addClass("ui-scrollview-view");
- }
-
- if ( this.options.scrollMethod === "translate" ) {
- if ( this._$view.css("transform") === undefined ) {
- this.options.scrollMethod = "position";
- }
- }
-
- this._$clip.css( "overflow", "hidden" );
- this._makePositioned( this._$clip );
-
- this._makePositioned( this._$view );
- this._$view.css( { left: 0, top: 0 } );
-
- this._view_height = this._getViewHeight();
-
- this._sx = 0;
- this._sy = 0;
-
- direction = this.options.direction;
-
- this._hTracker = ( direction !== "y" ) ?
- new MomentumTracker( this.options ) : null;
- this._vTracker = ( direction !== "x" ) ?
- new MomentumTracker( this.options ) : null;
-
- this._timerInterval = this.options.timerInterval;
- this._timerID = 0;
-
- this._timerCB = function () {
- self._handleMomentumScroll();
- };
-
- this._add_event();
- this._add_scrollbar();
- this._add_scroll_jump();
- this._add_overflow_indicator();
- },
-
- _startMScroll: function ( speedX, speedY ) {
- var keepGoing = false,
- duration = this.options.scrollDuration,
- ht = this._hTracker,
- vt = this._vTracker,
- c,
- v;
-
- this._$clip.trigger( this.options.startEventName );
-
- if ( ht ) {
- c = this._$clip.width();
- v = this._getViewWidth();
-
- if ( (( this._sx === 0 && speedX > 0 ) ||
- ( this._sx === -(v - c) && speedX < 0 )) &&
- v > c ) {
- return;
- }
-
- ht.start( this._sx, speedX,
- duration, (v > c) ? -(v - c) : 0, 0 );
- keepGoing = !ht.done();
- }
-
- if ( vt ) {
- c = this._$clip.height();
- v = this._getViewHeight();
-
- if ( (( this._sy === 0 && speedY > 0 ) ||
- ( this._sy === -(v - c) && speedY < 0 )) &&
- v > c ) {
- return;
- }
-
- vt.start( this._sy, speedY,
- duration, (v > c) ? -(v - c) : 0, 0 );
- keepGoing = keepGoing || !vt.done();
- }
-
- if ( keepGoing ) {
- this._timerID = setTimeout( this._timerCB, this._timerInterval );
- } else {
- this._stopMScroll();
- }
- },
-
- _stopMScroll: function () {
- if ( this._timerID ) {
- this._$clip.trigger( this.options.stopEventName );
- clearTimeout( this._timerID );
- }
- this._timerID = 0;
-
- if ( this._vTracker ) {
- this._vTracker.reset();
- }
-
- if ( this._hTracker ) {
- this._hTracker.reset();
- }
-
- this._hideScrollBars();
- this._hideOverflowIndicator();
- },
-
- _handleMomentumScroll: function () {
- var keepGoing = false,
- x = 0,
- y = 0,
- scroll_height = 0,
- self = this,
- vt = this._vTracker,
- ht = this._hTracker;
-
- if ( this._outerScrolling ) {
- return;
- }
-
- if ( vt ) {
- vt.update( this.options.overshootEnable );
- y = vt.getPosition();
- keepGoing = !vt.done();
-
- if ( vt.getRemained() > this.options.overshootDuration ) {
- scroll_height = this._getViewHeight() - this._$clip.height();
-
- if ( !vt.isAvail() ) {
- if ( this._speedY > 0 ) {
- this._outerScroll( vt.getRemained() / 3, scroll_height );
- } else {
- this._outerScroll( y - vt.getRemained() / 3, scroll_height );
- }
- } else if ( vt.isMin() ) {
- this._outerScroll( y - vt.getRemained() / 3, scroll_height );
-
- } else if ( vt.isMax() ) {
- this._outerScroll( vt.getRemained() / 3, scroll_height );
- }
- }
- }
-
- if ( ht ) {
- ht.update( this.options.overshootEnable );
- x = ht.getPosition();
- keepGoing = keepGoing || !ht.done();
- }
-
- this._setScrollPosition( x, y );
- this._$clip.trigger( this.options.updateEventName,
- [ { x: x, y: y } ] );
-
- if ( keepGoing ) {
- this._timerID = setTimeout( this._timerCB, this._timerInterval );
- } else {
- this._stopMScroll();
- }
- },
-
- _setElementTransform: function ( $ele, x, y, duration ) {
- var translate,
- transition;
-
- if ( !duration || duration === undefined ) {
- transition = "none";
- } else {
- transition = "-webkit-transform " + duration / 1000 + "s ease-out";
- }
-
- if ( $.support.cssTransform3d ) {
- translate = "translate3d(" + x + "," + y + ", 0px)";
- } else {
- translate = "translate(" + x + "," + y + ")";
- }
-
- $ele.css({
- "-moz-transform": translate,
- "-webkit-transform": translate,
- "-ms-transform": translate,
- "-o-transform": translate,
- "transform": translate,
- "-webkit-transition": transition
- });
- },
-
- _setEndEffect: function ( dir ) {
- var scroll_height = this._getViewHeight() - this._$clip.height();
-
- if ( this._softkeyboard ) {
- if ( this._effect_dir ) {
- this._outerScroll( -scroll_height - this._softkeyboardHeight,
- scroll_height );
- } else {
- this._outerScroll( this._softkeyboardHeight, scroll_height );
- }
- return;
- }
-
- if ( dir === "in" ) {
- if ( this._endEffect ) {
- return;
- }
-
- this._endEffect = true;
- this._setOverflowIndicator( this._effect_dir );
- this._showOverflowIndicator();
- } else if ( dir === "out" ) {
- if ( !this._endEffect ) {
- return;
- }
-
- this._endEffect = false;
- } else {
- this._endEffect = false;
- this._setOverflowIndicator();
- this._showOverflowIndicator();
- }
- },
-
- _setCalibration: function ( x, y ) {
- if ( this.options.overshootEnable ) {
- this._sx = x;
- this._sy = y;
- return;
- }
-
- var $v = this._$view,
- $c = this._$clip,
- dirLock = this._directionLock,
- scroll_height = 0,
- scroll_width = 0;
-
- if ( dirLock !== "y" && this._hTracker ) {
- scroll_width = $v.width() - $c.width();
-
- if ( x >= 0 ) {
- this._sx = 0;
- } else if ( x < -scroll_width ) {
- this._sx = -scroll_width;
- } else {
- this._sx = x;
- }
-
- if ( scroll_width < 0 ) {
- this._sx = 0;
- }
- }
-
- if ( dirLock !== "x" && this._vTracker ) {
- scroll_height = this._getViewHeight() - $c.height();
-
- if ( y > 0 ) {
- this._sy = 0;
-
- this._effect_dir = 0;
- this._setEndEffect( "in" );
- } else if ( y < -scroll_height ) {
- this._sy = -scroll_height;
-
- this._effect_dir = 1;
- this._setEndEffect( "in" );
- } else {
- if ( this._endEffect && this._sy !== y ) {
- this._setEndEffect();
- }
-
- this._sy = y;
- }
-
- if ( scroll_height < 0 ) {
- this._sy = 0;
- }
- }
- },
-
- _setScrollPosition: function ( x, y, duration ) {
- var $v = this._$view,
- sm = this.options.scrollMethod,
- $vsb = this._$vScrollBar,
- $hsb = this._$hScrollBar,
- $sbt;
-
- this._setCalibration( x, y );
-
- x = this._sx;
- y = this._sy;
-
- if ( sm === "translate" ) {
- this._setElementTransform( $v, x + "px", y + "px", duration );
- } else {
- $v.css( {left: x + "px", top: y + "px"} );
- }
-
- if ( $vsb ) {
- $sbt = $vsb.find(".ui-scrollbar-thumb");
-
- if ( sm === "translate" ) {
- this._setElementTransform( $sbt, "0px",
- -y / this._getViewHeight() * $sbt.parent().height() + "px",
- duration );
- } else {
- $sbt.css( "top", -y / this._getViewHeight() * 100 + "%" );
- }
- }
-
- if ( $hsb ) {
- $sbt = $hsb.find(".ui-scrollbar-thumb");
-
- if ( sm === "translate" ) {
- this._setElementTransform( $sbt,
- -x / $v.width() * $sbt.parent().width() + "px", "0px",
- duration);
- } else {
- $sbt.css("left", -x / $v.width() * 100 + "%");
- }
- }
- },
-
- _outerScroll: function ( y, scroll_height ) {
- var self = this,
- top = $( window ).scrollTop() - window.screenTop,
- sy = 0,
- duration = this.options.snapbackDuration,
- start = getCurrentTime(),
- tfunc;
-
- if ( !this.options.outerScrollEnable ) {
- return;
- }
-
- if ( this._$clip.jqmData("scroll") !== "y" ) {
- return;
- }
-
- if ( this._outerScrolling ) {
- return;
- }
-
- if ( y > 0 ) {
- sy = ( window.screenTop ? window.screenTop : -y );
- } else if ( y < -scroll_height ) {
- sy = -y - scroll_height;
- } else {
- return;
- }
-
- tfunc = function () {
- var elapsed = getCurrentTime() - start;
-
- if ( elapsed >= duration ) {
- window.scrollTo( 0, top + sy );
- self._outerScrolling = undefined;
-
- self._stopMScroll();
- } else {
- ec = $.easing.easeOutQuad( elapsed / duration,
- elapsed, 0, 1, duration );
-
- window.scrollTo( 0, top + ( sy * ec ) );
- self._outerScrolling = setTimeout( tfunc, self._timerInterval );
- }
- };
- this._outerScrolling = setTimeout( tfunc, self._timerInterval );
- },
-
- _scrollTo: function ( x, y, duration ) {
- var self = this,
- start = getCurrentTime(),
- efunc = $.easing.easeOutQuad,
- sx = this._sx,
- sy = this._sy,
- dx = x - sx,
- dy = y - sy,
- tfunc;
-
- x = -x;
- y = -y;
-
- tfunc = function () {
- var elapsed = getCurrentTime() - start,
- ec;
-
- if ( elapsed >= duration ) {
- self._timerID = 0;
- self._setScrollPosition( x, y );
- } else {
- ec = efunc( elapsed / duration, elapsed, 0, 1, duration );
-
- self._setScrollPosition( sx + ( dx * ec ), sy + ( dy * ec ) );
- self._timerID = setTimeout( tfunc, self._timerInterval );
- }
- };
-
- this._timerID = setTimeout( tfunc, this._timerInterval );
- },
-
- scrollTo: function ( x, y, duration ) {
- this._stopMScroll();
- this._didDrag = false;
-
- if ( !duration || this.options.scrollMethod === "translate" ) {
- this._setScrollPosition( x, y, duration );
- } else {
- this._scrollTo( x, y, duration );
- }
- },
-
- getScrollPosition: function () {
- return { x: -this._sx, y: -this._sy };
- },
-
- skipDragging: function ( value ) {
- this._skip_dragging = value;
- },
-
- _getScrollHierarchy: function () {
- var svh = [],
- d;
-
- this._$clip.parents( ".ui-scrollview-clip").each( function () {
- d = $( this ).jqmData("scrollview");
- if ( d ) {
- svh.unshift( d );
- }
- } );
- return svh;
- },
-
- _getAncestorByDirection: function ( dir ) {
- var svh = this._getScrollHierarchy(),
- n = svh.length,
- sv,
- svdir;
-
- while ( 0 < n-- ) {
- sv = svh[n];
- svdir = sv.options.direction;
-
- if (!svdir || svdir === dir) {
- return sv;
- }
- }
- return null;
- },
-
- _handleDragStart: function ( e, ex, ey ) {
- this._stopMScroll();
-
- this._didDrag = false;
- this._skip_dragging = false;
-
- var target = $( e.target ),
- self = this,
- $c = this._$clip,
- svdir = this.options.direction;
-
- /* should prevent the default behavior when click the button */
- this._is_button = target.is( '.ui-btn' ) ||
- target.is( '.ui-btn-text' ) ||
- target.is( '.ui-btn-inner' ) ||
- target.is( '.ui-btn-inner .ui-icon' );
-
- /* should prevent the default behavior when click the slider */
- if ( target.parents('.ui-slider').length || target.is('.ui-slider') ) {
- this._skip_dragging = true;
- return;
- }
-
- if ( target.is('textarea') ) {
- target.bind( "scroll", function () {
- self._skip_dragging = true;
- target.unbind("scroll");
- });
- }
-
- /*
- * We need to prevent the default behavior to
- * suppress accidental selection of text, etc.
- */
- this._is_inputbox = target.is(':input') ||
- target.parents(':input').length > 0;
-
- if ( this._is_inputbox ) {
- target.one( "resize.scrollview", function () {
- if ( ey > $c.height() ) {
- self.scrollTo( -ex, self._sy - ey + $c.height(),
- self.options.snapbackDuration );
- }
- });
- }
-
- if ( this.options.eventType === "mouse" && !this._is_inputbox && !this._is_button ) {
- e.preventDefault();
- }
-
- this._lastX = ex;
- this._lastY = ey;
- this._startY = ey;
- this._doSnapBackX = false;
- this._doSnapBackY = false;
- this._speedX = 0;
- this._speedY = 0;
- this._directionLock = "";
-
- this._lastMove = 0;
- this._enableTracking();
-
- this._set_scrollbar_size();
- },
-
- _propagateDragMove: function ( sv, e, ex, ey, dir ) {
- this._hideScrollBars();
- this._hideOverflowIndicator();
- this._disableTracking();
- sv._handleDragStart( e, ex, ey );
- sv._directionLock = dir;
- sv._didDrag = this._didDrag;
- },
-
- _handleDragMove: function ( e, ex, ey ) {
- if ( this._skip_dragging ) {
- return;
- }
-
- if ( !this._dragging ) {
- return;
- }
-
- if ( !this._is_inputbox && !this._is_button ) {
- e.preventDefault();
- }
-
- var mt = this.options.moveThreshold,
- dx = ex - this._lastX,
- dy = ey - this._lastY,
- svdir = this.options.direction,
- dir = null,
- x,
- y,
- sv,
- scope,
- newX,
- newY,
- dirLock;
-
- this._lastMove = getCurrentTime();
-
- if ( !this._directionLock ) {
- x = Math.abs( dx );
- y = Math.abs( dy );
-
- if ( x < mt && y < mt ) {
- return false;
- }
-
- if ( x < y && (x / y) < 0.5 ) {
- dir = "y";
- } else if ( x > y && (y / x) < 0.5 ) {
- dir = "x";
- }
-
- if ( svdir && dir && svdir !== dir ) {
- /*
- * This scrollview can't handle the direction the user
- * is attempting to scroll. Find an ancestor scrollview
- * that can handle the request.
- */
-
- sv = this._getAncestorByDirection( dir );
- if ( sv ) {
- this._propagateDragMove( sv, e, ex, ey, dir );
- return false;
- }
- }
-
- this._directionLock = svdir || (dir || "none");
- }
-
- newX = this._sx;
- newY = this._sy;
- dirLock = this._directionLock;
-
- if ( dirLock !== "y" && this._hTracker ) {
- x = this._sx;
- this._speedX = dx;
- newX = x + dx;
-
- this._doSnapBackX = false;
-
- scope = ( newX > 0 || newX < this._maxX );
-
- if ( scope && dirLock === "x" ) {
- sv = this._getAncestorByDirection("x");
- if ( sv ) {
- this._setScrollPosition( newX > 0 ?
- 0 : this._maxX, newY );
- this._propagateDragMove( sv, e, ex, ey, dir );
- return false;
- }
-
- newX = x + ( dx / 2 );
- this._doSnapBackX = true;
- }
- }
-
- if ( dirLock !== "x" && this._vTracker ) {
- if ( Math.abs( this._startY - ey ) < mt && dirLock !== "xy" ) {
- return;
- }
-
- y = this._sy;
- this._speedY = dy;
- newY = y + dy;
-
- this._doSnapBackY = false;
-
- scope = ( newY > 0 || newY < this._maxY );
-
- if ( scope && dirLock === "y" ) {
- sv = this._getAncestorByDirection("y");
- if ( sv ) {
- this._setScrollPosition( newX,
- newY > 0 ? 0 : this._maxY );
- this._propagateDragMove( sv, e, ex, ey, dir );
- return false;
- }
-
- newY = y + ( dy / 2 );
- this._doSnapBackY = true;
- }
- }
-
- if ( this.options.overshootEnable === false ) {
- this._doSnapBackX = false;
- this._doSnapBackY = false;
- }
-
- this._lastX = ex;
- this._lastY = ey;
-
- this._setScrollPosition( newX, newY );
-
- if ( this._didDrag === false ) {
- this._didDrag = true;
- this._showScrollBars();
- this._showOverflowIndicator();
-
- this._$clip.parents(".ui-scrollview-clip").each( function () {
- $( this ).scrollview( "skipDragging", true );
- } );
- }
- },
-
- _handleDragStop: function ( e ) {
- var self = this;
-
- if ( this._skip_dragging ) {
- return;
- }
-
- var l = this._lastMove,
- t = getCurrentTime(),
- doScroll = (l && (t - l) <= this.options.moveIntervalThreshold),
- sx = ( this._hTracker && this._speedX && doScroll ) ?
- this._speedX : ( this._doSnapBackX ? 1 : 0 ),
- sy = ( this._vTracker && this._speedY && doScroll ) ?
- this._speedY : ( this._doSnapBackY ? 1 : 0 ),
- svdir = this.options.direction,
- x,
- y;
-
- if ( sx || sy ) {
- if ( !this._setGestureScroll( sx, sy ) ) {
- this._startMScroll( sx, sy );
- }
- } else {
- this._hideScrollBars();
- this._hideOverflowIndicator();
- }
-
- this._disableTracking();
-
- if ( this._endEffect ) {
- setTimeout( function () {
- self._setEndEffect( "out" );
- self._hideScrollBars();
- self._hideOverflowIndicator();
- }, 300 );
- }
-
- return !this._didDrag;
- },
-
- _setGestureScroll: function ( sx, sy ) {
- var self = this,
- reset = function () {
- clearTimeout( self._gesture_timer );
- self._gesture_dir = 0;
- self._gesture_timer = undefined;
- },
- direction = {
- top: 0,
- bottom: 1,
- left: 2,
- right: 3
- };
-
- if ( !sy && !sx ) {
- return false;
- }
-
- if ( Math.abs( sx ) > Math.abs( sy ) ) {
- dir = sx > 0 ? direction.left : direction.right;
- } else {
- dir = sy > 0 ? direction.top : direction.bottom;
- }
-
- if ( !this._gesture_timer ) {
- this._gesture_dir = dir;
-
- this._gesture_timer = setTimeout( function () {
- reset();
- }, 1000 );
-
- return false;
- }
-
- if ( this._gesture_dir !== dir ) {
- reset();
- return false;
- }
-
- return false;
- },
-
- _enableTracking: function () {
- this._dragging = true;
- },
-
- _disableTracking: function () {
- this._dragging = false;
- },
-
- _showScrollBars: function ( interval ) {
- var vclass = "ui-scrollbar-visible",
- self = this;
-
- if ( !this.options.showScrollBars ) {
- return;
- }
- if ( this._scrollbar_showed ) {
- return;
- }
-
- if ( this._$vScrollBar ) {
- this._$vScrollBar.addClass( vclass );
- }
- if ( this._$hScrollBar ) {
- this._$hScrollBar.addClass( vclass );
- }
-
- this._scrollbar_showed = true;
-
- if ( interval ) {
- setTimeout( function () {
- self._hideScrollBars();
- }, interval );
- }
- },
-
- _hideScrollBars: function () {
- var vclass = "ui-scrollbar-visible";
-
- if ( !this.options.showScrollBars ) {
- return;
- }
- if ( !this._scrollbar_showed ) {
- return;
- }
-
- if ( this._$vScrollBar ) {
- this._$vScrollBar.removeClass( vclass );
- }
- if ( this._$hScrollBar ) {
- this._$hScrollBar.removeClass( vclass );
- }
-
- this._scrollbar_showed = false;
- },
-
- _setOverflowIndicator: function ( dir ) {
- if ( dir === 1 ) {
- this._opacity_top = "0";
- this._opacity_bottom = "0.8";
- } else if ( dir === 0 ) {
- this._opacity_top = "0.8";
- this._opacity_bottom = "0";
- } else {
- this._opacity_top = "0.5";
- this._opacity_bottom = "0.5";
- }
- },
-
- _showOverflowIndicator: function () {
- if ( !this.options.overflowEnable || !this._overflowAvail || this._softkeyboard ) {
- return;
- }
-
- this._overflow_top.animate( { opacity: this._opacity_top }, 300 );
- this._overflow_bottom.animate( { opacity: this._opacity_bottom }, 300 );
-
- this._overflow_showed = true;
- },
-
- _hideOverflowIndicator: function () {
- if ( !this.options.overflowEnable || !this._overflowAvail || this._softkeyboard ) {
- return;
- }
-
- if ( this._overflow_showed === false ) {
- return;
- }
-
- this._overflow_top.animate( { opacity: 0 }, 300 );
- this._overflow_bottom.animate( { opacity: 0 }, 300 );
-
- this._overflow_showed = false;
- this._setOverflowIndicator();
- },
-
- _add_event: function () {
- var self = this,
- $c = this._$clip,
- $v = this._$view;
-
- if ( this.options.eventType === "mouse" ) {
- this._dragEvt = "mousedown mousemove mouseup click mousewheel";
-
- this._dragCB = function ( e ) {
- switch ( e.type ) {
- case "mousedown":
- return self._handleDragStart( e,
- e.clientX, e.clientY );
-
- case "mousemove":
- return self._handleDragMove( e,
- e.clientX, e.clientY );
-
- case "mouseup":
- return self._handleDragStop( e );
-
- case "click":
- return !self._didDrag;
-
- case "mousewheel":
- var old = self.getScrollPosition();
- self.scrollTo( -old.x,
- -(old.y - e.originalEvent.wheelDelta) );
- break;
- }
- };
- } else {
- this._dragEvt = "touchstart touchmove touchend click";
-
- this._dragCB = function ( e ) {
- var touches = e.originalEvent.touches;
-
- switch ( e.type ) {
- case "touchstart":
- if ( touches.length != 1) {
- return;
- }
-
- return self._handleDragStart( e,
- touches[0].pageX, touches[0].pageY );
-
- case "touchmove":
- if ( touches.length != 1) {
- return;
- }
-
- return self._handleDragMove( e,
- touches[0].pageX, touches[0].pageY );
-
- case "touchend":
- if ( touches.length != 0) {
- return;
- }
+ *
+ * This software is licensed under the MIT licence (as defined by the OSI at
+ * http://www.opensource.org/licenses/mit-license.php)
+ *
+ * ***************************************************************************
+ * Copyright (C) 2011 by Intel Corporation Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ */
- return self._handleDragStop( e );
+// Ensure that the given namespace is defined. If not, define it to be an empty object.
+// This is kinda like the mkdir -p command.
- case "click":
- return !self._didDrag;
- }
- };
+var ensureNS = (function () {
+ var internalCache = {};
+ return function ensureNS (ns) { // name just for debugging purposes
+ var nsArr = ns.split(".").reverse(),
+ nsSoFar = "",
+ buffer = "",
+ leaf = "",
+ l = nsArr.length;
+ while(--l >= 0) {
+ leaf = nsArr[l];
+ nsSoFar = nsSoFar + (nsSoFar.length > 0 ? "." : "") + leaf;
+ if (!internalCache[nsSoFar]) {
+ internalCache[nsSoFar] = true;
+ buffer += "!window." + nsSoFar + ' && (window.' + nsSoFar + " = {});\n";
}
+ }
+ buffer.length && (new Function(buffer))();
+ };
+})();
- $v.bind( this._dragEvt, this._dragCB );
-
- $v.bind( "keydown", function ( e ) {
- var elem,
- elem_top,
- scroll_top = $( window ).scrollTop() - window.screenTop,
- screen_h;
-
- if ( e.keyCode == 9 ) {
- return false;
- }
-
- elem = $c.find(".ui-focus");
-
- if ( elem === undefined ) {
- return;
- }
-
- elem_top = elem.offset().top - scroll_top;
- screen_h = $c.offset().top + $c.height() - elem.height();
-
- if ( self._softkeyboard ) {
- screen_h -= self._softkeyboardHeight;
- }
-
- if ( ( elem_top < $c.offset().top ) || ( elem_top > screen_h ) ) {
- self.scrollTo( 0, self._sy -
- ( elem_top - $c.offset().top - elem.height() ) );
- }
-
- return;
- });
-
- $v.bind( "keyup", function ( e ) {
- var input,
- elem,
- elem_top,
- scroll_top = $( window ).scrollTop() - window.screenTop,
- screen_h;
-
- if ( e.keyCode != 9 ) {
- return;
- }
-
- /* Tab Key */
-
- input = $( this ).find(":input");
-
- for ( i = 0; i < input.length; i++ ) {
- if ( !$( input[i] ).hasClass("ui-focus") ) {
- continue;
- }
-
- if ( i + 1 == input.length ) {
- elem = $( input[0] );
- } else {
- elem = $( input[i + 1] );
- }
-
- elem_top = elem.offset().top - scroll_top;
- screen_h = $c.offset().top + $c.height() - elem.height();
-
- if ( self._softkeyboard ) {
- screen_h -= self._softkeyboardHeight;
- }
-
- if ( ( elem_top < 0 ) || ( elem_top > screen_h ) ) {
- self.scrollTo( 0, self._sy - elem_top +
- elem.height() + $c.offset().top, 0);
- }
-
- elem.focus();
-
- break;
- }
-
- return false;
- });
-
- $c.bind( "updatelayout", function ( e ) {
- var sy,
- vh,
- view_h = self._getViewHeight();
-
- if ( !$c.height() || !view_h ) {
- self.scrollTo( 0, 0, 0 );
- return;
- }
-
- sy = $c.height() - view_h;
- vh = view_h - self._view_height;
-
- self._view_height = view_h;
-
- if ( vh == 0 || vh > $c.height() / 2 ) {
- return;
- }
-
- if ( sy > 0 ) {
- self.scrollTo( 0, 0, 0 );
- } else if ( self._sy - sy <= -vh ) {
- self.scrollTo( 0, self._sy,
- self.options.snapbackDuration );
- } else if ( self._sy - sy <= vh + self.options.moveThreshold ) {
- self.scrollTo( 0, sy,
- self.options.snapbackDuration );
- }
- });
-
- $( window ).bind( "resize", function ( e ) {
- var focused,
- view_h = self._getViewHeight();
-
- if ( $(".ui-page-active").get(0) !== $c.closest(".ui-page").get(0) ) {
- return;
- }
-
- if ( !$c.height() || !view_h ) {
- return;
- }
-
- focused = $c.find(".ui-focus");
-
- if ( focused ) {
- focused.trigger("resize.scrollview");
- }
- /* calibration - after triggered throttledresize */
- setTimeout( function () {
- if ( self._sy < $c.height() - self._getViewHeight() ) {
- self.scrollTo( 0, $c.height() - self._getViewHeight(),
- self.options.overshootDuration );
- }
- }, 260 );
+\r
+/* ***************************************************************************\r
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.\r
+ *\r
+ * Permission is hereby granted, free of charge, to any person obtaining a\r
+ * copy of this software and associated documentation files (the "Software"),\r
+ * to deal in the Software without restriction, including without limitation\r
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,\r
+ * and/or sell copies of the Software, and to permit persons to whom the\r
+ * Software is furnished to do so, subject to the following conditions:\r
+ *\r
+ * The above copyright notice and this permission notice shall be included in\r
+ * all copies or substantial portions of the Software.\r
+ *\r
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\r
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\r
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\r
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\r
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING\r
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER\r
+ * DEALINGS IN THE SOFTWARE.\r
+ * ***************************************************************************\r
+ *\r
+ * Authors: Hyunsook Park <hyunsook.park@samsung.com>\r
+ * Wonseop Kim <wonseop.kim@samsung.com>\r
+*/\r
+\r
+( function ( $, undefined ) {\r
+ $.webgl = {};\r
+\r
+ $.webgl.shader = {\r
+ _vertexShader: null,\r
+ _fragmentShader: null,\r
+\r
+ deleteShaders: function ( gl ) {\r
+ gl.deleteShader( this._vertexShader );\r
+ gl.deleteShader( this._fragmentShader );\r
+ },\r
+\r
+ addShaderProgram : function ( gl, vs, fs, isFile ) {\r
+ var shaderProgram,\r
+ vertexShaderSource = {},\r
+ fragmentShaderSource = {};\r
+\r
+ if ( isFile ) {\r
+ vertexShaderSource = this.loadShaderFile( vs );\r
+ fragmentShaderSource = this.loadShaderFile( fs );\r
+ } else {\r
+ vertexShaderSource.source = vs;\r
+ fragmentShaderSource.source = fs;\r
+ }\r
+\r
+ this._vertexShader = this.getShader( gl, gl.VERTEX_SHADER, vertexShaderSource );\r
+ this._fragmentShader = this.getShader( gl, gl.FRAGMENT_SHADER, fragmentShaderSource );\r
+\r
+ shaderProgram = gl.createProgram();\r
+ gl.attachShader( shaderProgram, this._vertexShader);\r
+ gl.attachShader( shaderProgram, this._fragmentShader);\r
+ gl.linkProgram( shaderProgram );\r
+\r
+ if ( !gl.getProgramParameter( shaderProgram, gl.LINK_STATUS ) ) {\r
+ window.alert( "Could not initialize Shaders!" );\r
+ }\r
+ return shaderProgram;\r
+ },\r
+\r
+ loadShaderFile : function ( path ) {\r
+ var cache = null;\r
+ $.ajax({\r
+ async : false,\r
+ url : path,\r
+ success : function ( result ) {\r
+ cache = {\r
+ source: result\r
+ };\r
+ }\r
+ });\r
+ return cache;\r
+ },\r
+\r
+ getShader: function ( gl, type, script ) {\r
+ var shader;\r
+\r
+ if ( !gl || !type || !script ) {\r
+ return null;\r
+ }\r
+\r
+ shader = gl.createShader( type );\r
+\r
+ gl.shaderSource( shader, script.source );\r
+ gl.compileShader( shader );\r
+\r
+ if ( !gl.getShaderParameter( shader, gl.COMPILE_STATUS ) ) {\r
+ window.alert( gl.getShaderInfoLog( shader ) );\r
+ gl.deleteShader( shader );\r
+ return null;\r
+ }\r
+ return shader;\r
+ }\r
+ };\r
+\r
+ $.webgl.buffer = {\r
+ attribBufferData: function ( gl, attribArray ) {\r
+ var attribBuffer = gl.createBuffer();\r
+\r
+ gl.bindBuffer( gl.ARRAY_BUFFER, attribBuffer );\r
+ gl.bufferData( gl.ARRAY_BUFFER, attribArray, gl.STATIC_DRAW );\r
+ gl.bindBuffer( gl.ARRAY_BUFFER, null );\r
+\r
+ return attribBuffer;\r
+ }\r
+ };\r
+\r
+} ( jQuery ) );\r
+\r
- self._view_height = view_h;
- });
- $( window ).bind( "vmouseout", function ( e ) {
- var drag_stop = false;
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Authors: Hyunsook Park <hyunsook.park@samsung.com>
+ * Wonseop Kim <wonseop.kim@samsung.com>
+*/
- if ( $(".ui-page-active").get(0) !== $c.closest(".ui-page").get(0) ) {
- return;
- }
+( function ( $, window, undefined ) {
+ var HALF_PI = Math.PI / 2,
+ DEFAULT_STEP = 0.001,
+ MotionPath = {},
+ vec3 = window.vec3,
+ arcLength3d = function ( p0, p1 ) {
+ var d = [ p1[0] - p0[0], p1[1] - p0[1], p1[2] - p0[2] ],
+ value = Math.sqrt( d[0] * d[0] + d[1] * d[1] + d[2] * d[2] );
+ return value;
+ };
- if ( !self._dragging ) {
- return;
- }
+ MotionPath.base = function () {};
+ MotionPath.base.prototype = {
+ points: [],
+ step: DEFAULT_STEP,
+ length: 0,
+ levels: [],
+ init: function ( data ) {},
+ calculateLevel: function ( maxLevel ) {},
+ calculateTotalLength: function () {},
+ getPosition: function ( percent ) {},
+ getPercent: function ( start, interval ) {},
+ getAngle: function ( percent ) {}
+ };
- if ( e.pageX < 0 || e.pageX > $( window ).width() ) {
- drag_stop = true;
- }
+ MotionPath.bezier2d = function () {};
+ MotionPath.bezier2d.prototype = $.extend( true, {}, MotionPath.base.prototype, {
+ init: function ( data ) {
+ this.points = data.points;
+ this.step = data.step || DEFAULT_STEP;
+ this.length = this.calculateTotalLength();
+ this.levels = this.calculateLevel( data.maxLevel ) || [];
+ },
- if ( e.pageY < 0 || e.pageY > $( window ).height() ) {
- drag_stop = true;
- }
+ calculateLevel: function ( maxLevel ) {
+ var totalLength = this.length,
+ interval = totalLength / maxLevel,
+ levels = [],
+ i;
- if ( drag_stop ) {
- self._hideScrollBars();
- self._hideOverflowIndicator();
- self._disableTracking();
- }
- });
+ if ( !maxLevel ) {
+ return null;
+ }
- this._softkeyboard = false;
- this._softkeyboardHeight = 0;
+ for ( i = 0; i < maxLevel; i += 1 ) {
+ levels[maxLevel - i] = this.getPercent( 0, interval * i );
+ }
- window.addEventListener( "softkeyboardchange", function ( e ) {
- if ( $(".ui-page-active").get(0) !== $c.closest(".ui-page").get(0) ) {
- return;
- }
+ return levels;
+ },
- self._softkeyboard = ( e.state === "on" ? true : false );
- self._softkeyboardHeight = parseInt( e.height ) *
- ( $( window ).width() / window.screen.availWidth );
- });
+ calculateTotalLength: function () {
+ var step = this.step,
+ current = this.getPosition( 0 ),
+ last = current,
+ length = 0,
+ percent;
+ for ( percent = step; percent <= 1; percent += step ) {
+ current = this.getPosition( percent );
+ length += arcLength3d( last, current );
+ last = current;
+ }
+ return length;
+ },
- $c.closest(".ui-page")
- .bind( "pageshow", function ( e ) {
- /* should be called after pagelayout */
- setTimeout( function () {
- self._view_height = self._getViewHeight();
- self._set_scrollbar_size();
- self._setScrollPosition( self._sx, self._sy );
- self._showScrollBars( 2000 );
- }, 0 );
- });
+ getPosition: function ( percent ) {
+ var points = this.points,
+ getValue = function ( p1, c1, c2, p2, t ) {
+ return Math.pow(1 - t, 3) * p1 +
+ 3 * t * Math.pow( 1 - t, 2 ) * c1 +
+ 3 * Math.pow( t, 2 ) * ( 1 - t ) * c2 +
+ Math.pow( t, 3 ) * p2;
+ },
+ result = [
+ getValue( points[0][0], points[1][0], points[2][0], points[3][0], percent ),
+ getValue( points[0][2], points[1][2], points[2][2], points[3][2], percent )
+ ];
+ return [ result[0], 0, result[1] ];
},
- _add_scrollbar: function () {
- var $c = this._$clip,
- prefix = "<div class=\"ui-scrollbar ui-scrollbar-",
- suffix = "\"><div class=\"ui-scrollbar-track\"><div class=\"ui-scrollbar-thumb\"></div></div></div>";
-
- if ( !this.options.showScrollBars ) {
- return;
- }
+ getPercent: function ( start, interval ) {
+ var step = this.step,
+ current = this.getPosition( start = start || 0 ),
+ last = current,
+ targetLength = start + interval,
+ length = 0,
+ percent;
- if ( this._vTracker ) {
- $c.append( prefix + "y" + suffix );
- this._$vScrollBar = $c.children(".ui-scrollbar-y");
- }
- if ( this._hTracker ) {
- $c.append( prefix + "x" + suffix );
- this._$hScrollBar = $c.children(".ui-scrollbar-x");
+ for ( percent = start + step; percent <= 1; percent += step ) {
+ current = this.getPosition( percent );
+ length += arcLength3d( last, current );
+ if ( length >= targetLength ) {
+ return percent;
+ }
+ last = current;
}
-
- this._scrollbar_showed = false;
+ return 1;
},
- _add_scroll_jump: function () {
- var $c = this._$clip,
- self = this,
- top_btn,
- left_btn;
+ getAngle: function ( percent ) {
+ var points = this.points,
+ getTangent = function ( p1, c1, c2, p2, t ) {
+ return 3 * t * t * ( -p1 + 3 * c1 - 3 * c2 + p2 ) + 6 * t * ( p1 - 2 * c1 + c2 ) + 3 * ( -p1 + c1 );
+ },
+ tx = getTangent( points[0][0], points[1][0], points[2][0], points[3][0], percent ),
+ ty = getTangent( points[0][2], points[1][2], points[2][2], points[3][2], percent );
+ return Math.atan2( tx, ty ) - HALF_PI;
+ }
- if ( !this.options.scrollJump ) {
- return;
- }
+ } );
- if ( this._vTracker ) {
- top_btn = $( '<div class="ui-scroll-jump-top-bg">' +
- '<div data-role="button" data-inline="true" data-icon="scrolltop" data-style="box"></div></div>' );
- $c.append( top_btn ).trigger("create");
+ // clamped cubic B-spline curve
+ // http://web.mit.edu/hyperbook/Patrikalakis-Maekawa-Cho/node17.html
+ // http://www.cs.mtu.edu/~shene/COURSES/cs3621/NOTES/spline/B-spline/bspline-curve-coef.html
+ MotionPath.bspline = function () {};
+ MotionPath.bspline.prototype = $.extend( true, {}, MotionPath.base.prototype, {
+ _degree: 3,
+ _numberOfControls : 0,
+ _knotVectors: [],
+ _numberOfKnots: 0,
- top_btn.bind( "vclick", function () {
- self.scrollTo( 0, 0, self.options.overshootDuration );
- } );
- }
+ init: function ( data ) {
+ this.points = data.points;
+ this.step = data.step || DEFAULT_STEP;
+ this._numberOfPoints = this.points.length - 1;
+ this._numberOfKnots = this._numberOfPoints + this._degree + 1;
- if ( this._hTracker ) {
- left_btn = $( '<div class="ui-scroll-jump-left-bg">' +
- '<div data-role="button" data-inline="true" data-icon="scrollleft" data-style="box"></div></div>' );
- $c.append( left_btn ).trigger("create");
+ var deltaKnot = 1 / ( this._numberOfKnots - ( 2 * this._degree ) ),
+ v = deltaKnot,
+ i = 0;
- left_btn.bind( "vclick", function () {
- self.scrollTo( 0, 0, self.options.overshootDuration );
- } );
+ while ( i <= this._numberOfKnots ) {
+ if ( i <= this._degree ) {
+ this._knotVectors.push( 0 );
+ } else if ( i < this._numberOfKnots - this._degree + 1 ) {
+ this._knotVectors.push( v );
+ v += deltaKnot;
+ } else {
+ this._knotVectors.push( 1 );
+ }
+ i += 1;
}
+
+ this.length = this.calculateTotalLength();
+ this.levels = this.calculateLevel( data.maxLevel ) || [];
},
- _add_overflow_indicator: function () {
- if ( !this.options.overflowEnable ) {
- return;
- }
+ _Np: function ( percent, i, degree ) {
+ var knots = this._knotVectors,
+ A = 0,
+ B = 0,
+ denominator = 0,
+ N0 = function ( percent, i ) {
+ return ( ( knots[i] <= percent && percent < knots[i + 1] ) ? 1 : 0 );
+ };
- this._overflow_top = $( '<div class="ui-overflow-indicator-top"></div>' );
- this._overflow_bottom = $( '<div class="ui-overflow-indicator-bottom"></div>' );
+ if ( degree === 1 ) {
+ A = N0( percent, i );
+ B = N0( percent, i + 1 );
+ } else {
+ A = this._Np( percent, i, degree - 1 );
+ B = this._Np( percent, i + 1, degree - 1 );
+ }
- this._$clip.append( this._overflow_top );
- this._$clip.append( this._overflow_bottom );
+ denominator = knots[i + degree] - knots[i];
+ A *= ( denominator !== 0 ) ? ( ( percent - knots[i] ) / denominator ) : 0;
+ denominator = knots[i + degree + 1] - knots[i + 1];
+ B *= ( denominator !== 0 ) ? ( ( knots[i + degree + 1] - percent ) / denominator ) : 0;
- this._opacity_top = "0.5";
- this._opacity_bottom = "0.5";
- this._overflow_showed = false;
+ return A + B;
},
- _set_scrollbar_size: function () {
- var $c = this._$clip,
- $v = this._$view,
- cw = 0,
- vw = 0,
- ch = 0,
- vh = 0,
- thumb;
+ calculateLevel: function ( maxLevel ) {
+ var totalLength = this.length,
+ interval = totalLength / maxLevel,
+ levels = [],
+ i;
- if ( !this.options.showScrollBars ) {
- return;
+ if ( !maxLevel ) {
+ return null;
}
- if ( this._hTracker ) {
- cw = $c.width();
- vw = $v.width();
- this._maxX = cw - vw;
-
- if ( this._maxX > 0 ) {
- this._maxX = 0;
- }
- if ( this._$hScrollBar && vw ) {
- thumb = this._$hScrollBar.find(".ui-scrollbar-thumb");
- thumb.css( "width", (cw >= vw ? "0" :
- (Math.floor(cw / vw * 100) || 1) + "%") );
- }
+ for ( i = 0; i < maxLevel; i += 1 ) {
+ levels[maxLevel - i] = this.getPercent( 0, interval * i );
}
+ return levels;
+ },
- if ( this._vTracker ) {
- ch = $c.height();
- vh = this._getViewHeight();
- this._maxY = ch - vh;
-
- if ( this._maxY > 0 || vh === 0 ) {
- this._maxY = 0;
- }
- if ( ( this._$vScrollBar && vh ) || vh === 0 ) {
- thumb = this._$vScrollBar.find(".ui-scrollbar-thumb");
- thumb.css( "height", (ch >= vh ? "0" :
- (Math.floor(ch / vh * 100) || 1) + "%") );
+ calculateTotalLength: function () {
+ var step = this.step,
+ current = this.getPosition( 0 ),
+ last = current,
+ length = 0,
+ percent;
+ for ( percent = step; percent <= 1; percent += step ) {
+ current = this.getPosition( percent );
+ length += arcLength3d( last, current );
+ last = current;
+ }
+ return length;
+ },
- this._overflowAvail = !!thumb.height();
+ getPosition: function ( percent ) {
+ var result = [], i, j, sum;
+ percent = percent.toFixed( 4 );
+ for ( j = 0; j < 3; j += 1 ) {
+ sum = 0;
+ for ( i = 0; i <= this._numberOfPoints; i += 1 ) {
+ sum += this.points[i][j] * this._Np( percent, i, this._degree );
}
+ result[j] = sum;
}
- }
- });
-
- $.extend( MomentumTracker.prototype, {
- start: function ( pos, speed, duration, minPos, maxPos ) {
- var tstate = ( pos < minPos || pos > maxPos ) ?
- tstates.snapback : tstates.scrolling,
- pos_temp;
-
- this.state = ( speed !== 0 ) ? tstate : tstates.done;
- this.pos = pos;
- this.speed = speed;
- this.duration = ( this.state === tstates.snapback ) ?
- this.options.snapbackDuration : duration;
- this.minPos = minPos;
- this.maxPos = maxPos;
-
- this.fromPos = ( this.state === tstates.snapback ) ? this.pos : 0;
- pos_temp = ( this.pos < this.minPos ) ? this.minPos : this.maxPos;
- this.toPos = ( this.state === tstates.snapback ) ? pos_temp : 0;
-
- this.startTime = getCurrentTime();
- },
- reset: function () {
- this.state = tstates.done;
- this.pos = 0;
- this.speed = 0;
- this.minPos = 0;
- this.maxPos = 0;
- this.duration = 0;
- this.remained = 0;
+ return result;
},
- update: function ( overshootEnable ) {
- var state = this.state,
- cur_time = getCurrentTime(),
- duration = this.duration,
- elapsed = cur_time - this.startTime,
- dx,
- x,
- didOverShoot;
+ getPercent: function ( start, interval ) {
+ var step = this.step,
+ current = this.getPosition( start = start || 0 ),
+ last = current,
+ targetLength = start + interval,
+ length = 0,
+ percent;
- if ( state === tstates.done ) {
- return this.pos;
+ for ( percent = start + step; percent <= 1; percent += step ) {
+ current = this.getPosition( percent );
+ length += arcLength3d( last, current );
+ if ( length >= targetLength ) {
+ return percent;
+ }
+ last = current;
}
+ return 1;
+ },
- elapsed = elapsed > duration ? duration : elapsed;
+ getAngle: function ( percent ) {
+ var prev = this.getPosition( percent ),
+ next = this.getPosition( percent + 0.001 ),
+ dir = vec3.normalize( vec3.direction( prev, next ) ),
+ cosValue = vec3.dot( dir, [1, 0, 0] );
- this.remained = duration - elapsed;
+ return Math.acos( cosValue ) + Math.PI;
+ }
+ } );
- if ( state === tstates.scrolling || state === tstates.overshot ) {
- dx = this.speed *
- ( 1 - $.easing[this.easing]( elapsed / duration,
- elapsed, 0, 1, duration ) );
+ $.motionpath = function ( type, data ) {
+ var object = new MotionPath[type]();
+ object.init( data );
+ return object;
+ };
+} ( jQuery, window ) );
- x = this.pos + dx;
- didOverShoot = ( state === tstates.scrolling ) &&
- ( x < this.minPos || x > this.maxPos );
- if ( didOverShoot ) {
- x = ( x < this.minPos ) ? this.minPos : this.maxPos;
- }
+/**
+ @class Button
+ The button widget shows a control on the screen that you can use to generate an action event when it is pressed and released. This widget is coded with standard HTML anchor and input elements and then enhanced by jQueryMobile to make it more attractive and usable on a mobile device. Buttons can be used in Tizen as described in the jQueryMobile documentation for buttons.
- this.pos = x;
+ To add a button widget to the application, use the following code
- if ( state === tstates.overshot ) {
- if ( !overshootEnable ) {
- this.state = tstates.done;
- }
- if ( elapsed >= duration ) {
- this.state = tstates.snapback;
- this.fromPos = this.pos;
- this.toPos = ( x < this.minPos ) ?
- this.minPos : this.maxPos;
- this.duration = this.options.snapbackDuration;
- this.startTime = cur_time;
- elapsed = 0;
- }
- } else if ( state === tstates.scrolling ) {
- if ( didOverShoot && overshootEnable ) {
- this.state = tstates.overshot;
- this.speed = dx / 2;
- this.duration = this.options.overshootDuration;
- this.startTime = cur_time;
- } else if ( elapsed >= duration ) {
- this.state = tstates.done;
- }
- }
- } else if ( state === tstates.snapback ) {
- if ( elapsed >= duration ) {
- this.pos = this.toPos;
- this.state = tstates.done;
- } else {
- this.pos = this.fromPos + (( this.toPos - this.fromPos ) *
- $.easing[this.easing]( elapsed / duration,
- elapsed, 0, 1, duration ));
- }
- }
+ <div data-role="button" data-inline="true">Text Button Test</div>
+ <div data-role="button" data-inline="true" data-icon="plus" data-style="circle"></div>
+ <div data-role="button" data-inline="true" data-icon="plus" data-style="nobg"></div>
- return this.pos;
- },
+ The button can define callbacks for events as described in the jQueryMobile documentation for button events.<br/>
+ You can use methods with the button as described in the jQueryMobile documentation for button methods.
+*/
- done: function () {
- return this.state === tstates.done;
- },
+/**
+ @property {String} data-style
+ Defines the button style. <br/> The default value is box. If the value is set to circle, a circle-shaped button is created. If the value is set to nobg, a button is created without a background.
- isMin: function () {
- return this.pos === this.minPos;
- },
+*/
+/**
+ @property {String} data-icon
+ Defines an icon for a button. Tizen supports 12 icon styles: reveal, closed, opened, info, rename, call, warning, plus, minus, cancel, send, and favorite.
- isMax: function () {
- return this.pos === this.maxPos;
- },
+*/
- isAvail: function () {
- return !( this.minPos === this.maxPos );
- },
- getRemained: function () {
- return this.remained;
- },
- getPosition: function () {
- return this.pos;
- }
- });
+(function($, undefined) {
- $( document ).bind( 'pagecreate create', function ( e ) {
- var $page = $( e.target ),
- content_scroll = $page.find(".ui-content").jqmData("scroll");
+ensureNS("jQuery.mobile.tizen");
- /* content scroll */
- if ( $.support.scrollview === undefined ) {
- $.support.scrollview = true;
- }
+jQuery.extend( jQuery.mobile.tizen,
+{
+ _widgetPrototypes: {},
- if ( $.support.scrollview === true && content_scroll === undefined ) {
- content_scroll = "y";
- }
+ /*
+ * load the prototype for a widget.
+ *
+ * If @widget is a string, the function looks for @widget.prototype.html in the proto-html/ subdirectory of the
+ * framework's current theme and loads the file via AJAX into a string. Note that the file will only be loaded via
+ * AJAX once. If two widget instances based on the same @widget value are to be constructed, the second will be
+ * constructed from the cached copy of the prototype of the first instance.
+ *
+ * If @widget is not a string, it is assumed to be a hash containing at least one key, "proto", the value of which is
+ * the string to be used for the widget prototype. if another key named "key" is also provided, it will serve as the
+ * key under which to cache the prototype, so it need not be rendered again in the future.
+ *
+ * Given the string for the widget prototype, the following patterns occurring in the string are replaced:
+ *
+ * "${FRAMEWORK_ROOT}" - replaced with the path to the root of the framework
+ *
+ * The function then creates a jQuery $("<div>") object containing the prototype from the string.
+ *
+ * If @ui is not provided, the jQuery object containing the prototype is returned.
+ *
+ * If @ui is provided, it is assumed to be a (possibly multi-level) hash containing CSS selectors. For every level of
+ * the hash and for each string-valued key at that level, the CSS selector specified as the value is sought in the
+ * prototype jQuery object and, if found, the value of the key is replaced with the jQuery object resulting from the
+ * search. Additionally, if the CSS selector is of the form "#widgetid", the "id" attribute will be removed from the
+ * elements contained within the resulting jQuery object. The resulting hash is returned.
+ *
+ * Examples:
+ *
+ * 1.
+ * $.mobile.tizen.loadPrototype("mywidget") => Returns a <div> containing the structure from the file
+ * mywidget.prototype.html located in the current theme folder of the current framework.
+ *
+ * 2. $.mobile.tizen.loadPrototype("mywidget", ui):
+ * where ui is a hash that looks like this:
+ * ui = {
+ * element1: "<css selector 1>",
+ * element2: "<css selector 2>",
+ * group1: {
+ * group1element1: "<css selector 3>",
+ * group1element1: "<css selector 4>"
+ * }
+ * ...
+ * }
+ *
+ * In this case, after loading the prototype as in Example 1, loadPrototype will traverse @ui and replace the CSS
+ * selector strings with the result of the search for the selector string upon the prototype. If any of the CSS
+ * selectors are of the form "#elementid" then the "id" attribute will be stripped from the elements selected. This
+ * means that they will no longer be accessible via the selector used initially. @ui is then returned thus modified.
+ */
- if ( content_scroll !== "y" ) {
- content_scroll = "none";
- }
+ loadPrototype: function(widget, ui) {
+ var ret = undefined,
+ theScriptTag = $("script[data-framework-version][data-framework-root][data-framework-theme]"),
+ frameworkRootPath = theScriptTag.attr("data-framework-root") + "/" +
+ theScriptTag.attr("data-framework-version") + "/";
- $page.find(".ui-content").attr( "data-scroll", content_scroll );
+ function replaceVariables(s) {
+ return s.replace(/\$\{FRAMEWORK_ROOT\}/g, frameworkRootPath);
+ }
- $page.find(":jqmData(scroll)").not(".ui-scrollview-clip").each( function () {
- if ( $( this ).hasClass("ui-scrolllistview") ) {
- $( this ).scrolllistview();
- } else {
- var st = $( this ).jqmData("scroll"),
- dir = st && ( st.search(/^[xy]/) !== -1 ) ? st : null,
- content = $(this).hasClass("ui-content"),
- opts;
+ function fillObj(obj, uiProto) {
+ var selector;
- if ( st === "none" ) {
- return;
- }
+ for (var key in obj) {
+ if (typeof obj[key] === "string") {
+ selector = obj[key];
+ obj[key] = uiProto.find(obj[key]);
+ if (selector.substring(0, 1) === "#")
+ obj[key].removeAttr("id");
+ }
+ else
+ if (typeof obj[key] === "object")
+ obj[key] = fillObj(obj[key], uiProto);
+ }
+ return obj;
+ }
- opts = {
- direction: dir || undefined,
- overflowEnable: content,
- scrollMethod: $( this ).jqmData("scroll-method") || undefined,
- scrollJump: $( this ).jqmData("scroll-jump") || undefined
- };
+ /* If @widget is a string ... */
+ if (typeof widget === "string") {
+ /* ... try to use it as a key into the cached prototype hash ... */
+ ret = $.mobile.tizen._widgetPrototypes[widget];
+ if (ret === undefined) {
+ /* ... and if the proto was not found, try to load its definition ... */
+ var protoPath = frameworkRootPath + "proto-html" + "/" +
+ theScriptTag.attr("data-framework-theme");
+ $.ajax({
+ url: protoPath + "/" + widget + ".prototype.html",
+ async: false,
+ dataType: "html"
+ })
+ .success(function(data, textStatus, jqXHR) {
+ /* ... and if loading succeeds, cache it and use a copy of it ... */
+ $.mobile.tizen._widgetPrototypes[widget] = $("<div>").html(replaceVariables(data));
+ ret = $.mobile.tizen._widgetPrototypes[widget].clone();
+ });
+ }
+ }
+ /* Otherwise ... */
+ else {
+ /* ... if a key was provided ... */
+ if (widget.key !== undefined)
+ /* ... try to use it as a key into the cached prototype hash ... */
+ ret = $.mobile.tizen._widgetPrototypes[widget.key];
- $( this ).scrollview( opts );
- }
- });
- });
+ /* ... and if the proto was not found in the cache ... */
+ if (ret === undefined) {
+ /* ... and a proto definition string was provided ... */
+ if (widget.proto !== undefined) {
+ /* ... create a new proto from the definition ... */
+ ret = $("<div>").html(replaceVariables(widget.proto));
+ /* ... and if a key was provided ... */
+ if (widget.key !== undefined)
+ /* ... cache a copy of the proto under that key */
+ $.mobile.tizen._widgetPrototypes[widget.key] = ret.clone();
+ }
+ }
+ else
+ /* otherwise, if the proto /was/ found in the cache, return a copy of it */
+ ret = ret.clone();
+ }
- $( document ).bind( 'pageshow', function ( e ) {
- var $page = $( e.target ),
- scroll = $page.find(".ui-content").jqmData("scroll");
+ /* If the prototype was found/created successfully ... */
+ if (ret != undefined)
+ /* ... and @ui was provided */
+ if (ui != undefined)
+ /* ... return @ui, but replace the CSS selectors it contains with the elements they select */
+ ret = fillObj(ui, ret);
- if ( scroll === "y" ) {
- resizePageContentHeight( e.target );
- }
- });
+ return ret;
+ }
+});
+})(jQuery);
-}( jQuery, window, document ) );
+\r
+/* ***************************************************************************\r
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.\r
+ *\r
+ * Permission is hereby granted, free of charge, to any person obtaining a\r
+ * copy of this software and associated documentation files (the "Software"),\r
+ * to deal in the Software without restriction, including without limitation\r
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,\r
+ * and/or sell copies of the Software, and to permit persons to whom the\r
+ * Software is furnished to do so, subject to the following conditions:\r
+ *\r
+ * The above copyright notice and this permission notice shall be included in\r
+ * all copies or substantial portions of the Software.\r
+ *\r
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\r
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\r
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\r
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\r
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING\r
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER\r
+ * DEALINGS IN THE SOFTWARE.\r
+ * ***************************************************************************\r
+ *\r
+ * Authors: Hyunsook Park <hyunsook.park@samsung.com>\r
+ * Wonseop Kim <wonseop.kim@samsung.com>\r
+*/\r
+\r
+( function ( $, window, document, undefined ) {\r
+ var _canvas, _context;\r
+\r
+ function initCanvas() {\r
+ if (_context) {\r
+ return;\r
+ }\r
+ _canvas = document.createElement( 'canvas' );\r
+ _context = _canvas.getContext( '2d' );\r
+ }\r
+\r
+ function fileSystemErrorMessage( e ) {\r
+ var FileError = window.FileError,\r
+ msg = '';\r
+ switch ( e.code ) {\r
+ case FileError.QUOTA_EXCEEDED_ERR:\r
+ msg = 'QUOTA_EXCEEDED_ERR';\r
+ break;\r
+ case FileError.NOT_FOUND_ERR:\r
+ msg = 'NOT_FOUND_ERR';\r
+ break;\r
+ case FileError.SECURITY_ERR:\r
+ msg = 'SECURITY_ERR';\r
+ break;\r
+ case FileError.INVALID_MODIFICATION_ERR:\r
+ msg = 'INVALID_MODIFICATION_ERR';\r
+ break;\r
+ case FileError.INVALID_STATE_ERR:\r
+ msg = 'INVALID_STATE_ERR';\r
+ break;\r
+ default:\r
+ msg = 'Unknown Error';\r
+ break;\r
+ }\r
+ return msg;\r
+ }\r
+\r
+ function getInternalURLFromURL( url ) {\r
+ var internalURL = url.replace( /\//gi, "_" );\r
+ return internalURL;\r
+ }\r
+\r
+ function resize( imagewidth, imageheight, thumbwidth, thumbheight, fit ) {\r
+ var w = 0, h = 0, x = 0, y = 0,\r
+ widthratio = imagewidth / thumbwidth,\r
+ heightratio = imageheight / thumbheight,\r
+ maxratio = Math.max( widthratio, heightratio );\r
+\r
+ if ( fit ) {\r
+ w = thumbwidth;\r
+ h = thumbheight;\r
+ } else {\r
+ if ( maxratio > 1 ) {\r
+ w = imagewidth / maxratio;\r
+ h = imageheight / maxratio;\r
+ } else {\r
+ w = imagewidth;\r
+ h = imageheight;\r
+ }\r
+ x = ( thumbwidth - w ) / 2;\r
+ y = ( thumbheight - h ) / 2;\r
+ }\r
+\r
+ return { w: w, h: h, x: x, y: y };\r
+ }\r
+\r
+ function getThumbnail( img, thumbwidth, thumbheight, fit ) {\r
+ var dimensions, url;\r
+ initCanvas();\r
+ _canvas.width = thumbwidth;\r
+ _canvas.height = thumbheight;\r
+ dimensions = resize( img.width, img.height, thumbwidth, thumbheight, fit );\r
+ _context.fillStyle = "#000000";\r
+ _context.fillRect ( 0, 0, thumbwidth, thumbheight );\r
+ _context.drawImage( img, dimensions.x, dimensions.y, dimensions.w, dimensions.h );\r
+ url = _canvas.toDataURL();\r
+ return url;\r
+ }\r
+\r
+ $.imageloader = {\r
+ _grantedBytes: 1024 * 1024,\r
+ getThumbnail: function ( url, _callback ) {\r
+ var internalURL, canvasDataURI;\r
+ function errorHandler( e ) {\r
+ var msg = fileSystemErrorMessage( e );\r
+ if ( _callback ) {\r
+ _callback( ( msg === "NOT_FOUND_ERR" ) ? msg : null );\r
+ }\r
+ }\r
+\r
+ internalURL = getInternalURLFromURL( url );\r
+ try {\r
+ canvasDataURI = localStorage.getItem( internalURL );\r
+ if ( _callback ) {\r
+ _callback( ( canvasDataURI === null ) ? "NOT_FOUND_ERR" : canvasDataURI );\r
+ }\r
+ } catch ( e ) {\r
+ if ( _callback ) {\r
+ _callback( ( e.type === "non_object_property_load" ) ? "NOT_FOUND_ERR" : null );\r
+ }\r
+ }\r
+ },\r
+\r
+ setThumbnail: function ( url, _callback, thumbWidth, thumbHeight, fit ) {\r
+ var image, internalURL, canvasDataURI;\r
+ function errorHandler( e ) {\r
+ var msg = fileSystemErrorMessage( e );\r
+ if ( _callback ) {\r
+ _callback( ( msg === "NOT_FOUND_ERR" ) ? msg : null );\r
+ }\r
+ }\r
+\r
+ thumbWidth = thumbWidth || 128;\r
+ thumbHeight = thumbHeight || 128;\r
+ fit = fit || true;\r
+ image = new Image();\r
+ image.onload = function () {\r
+ internalURL = getInternalURLFromURL( url );\r
+ canvasDataURI = getThumbnail( this, thumbWidth, thumbHeight, fit );\r
+ try {\r
+ localStorage.setItem( internalURL, canvasDataURI );\r
+ if ( _callback ) {\r
+ _callback( canvasDataURI );\r
+ }\r
+ } catch ( e ) {\r
+ if ( _callback ) {\r
+ _callback( ( e.type === "non_object_property_load" ) ? "NOT_FOUND_ERR" : null );\r
+ }\r
+ }\r
+ };\r
+ image.src = url;\r
+ },\r
+\r
+ removeThumbnail: function ( url ) {\r
+ var internalURL;\r
+ function errorHandler( e ) {\r
+ fileSystemErrorMessage( e );\r
+ }\r
+\r
+ internalURL = getInternalURLFromURL( url );\r
+ try {\r
+ localStorage.removeItem( internalURL );\r
+ } catch ( e ) {\r
+ throw e;\r
+ }\r
+ }\r
+ };\r
+\r
+} ( jQuery, window, document ) );\r
+\r
/* ***************************************************************************
}( jQuery, this ) );
+\r
+/**\r
+ @class Checkbox\r
+ The check box widget shows a list of options on the screen where one or more can be selected. Check boxes can be used in Tizen as described in the jQueryMobile documentation for check boxes.<br/> To add a check box widget to the application, use the following code:\r
+\r
+ <input type="checkbox" name="mycheck" id="check-test" class="favorite" />\r
+ <label for="check-test">Favorite</label>\r
+ <input type="checkbox" name="check-favorite" id="check-test2" checked="checked" disabled="disabled" class="favorite" />\r
+ <label for="check-test2">Favorite Checked, Disabled</label>\r
+\r
+ The check box can define callbacks for events as described in the jQueryMobile documentation for check box events.\r
+ You can use methods with the check box as described in the jQueryMobile documentation for check box methods.\r
+\r
+*/\r
+/**\r
+ @property {String} class\r
+ Defines the check box style. <br/> The default value is check. If the value is set to favorite, a star-shaped check box is created.\r
+*/\r
+\r
+
+
+/*
+ *
+ * This software is licensed under the MIT licence (as defined by the OSI at
+ * http://www.opensource.org/licenses/mit-license.php)
+ *
+ * ***************************************************************************
+ * Copyright (C) 2011 by Intel Corporation Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ */
+
+// Add markup for labels
+
+
+(function($, undefined) {
+
+$(document).bind("pagecreate create", function(e) {
+ $(":jqmData(role='label')", e.target).not(":jqmData(role='none'), :jqmData(role='nojs')").each(function() {
+ $(this).addClass("jquery-mobile-ui-label")
+ .html($("<span>", {"class": "jquery-mobile-ui-label-text"}).text($(this).text()));
+ });
+});
+
+})(jQuery);
+
+
+
/* ***************************************************************************
* style : normal, check
listDividerLine : true
},
- _create: function () {
+ _create: function () {
+
+ var $listdivider = this.element,
+ openStatus = true,
+ expandSrc,
+ listDividerLine = true,
+ style = $listdivider.attr( "data-style" );
+
+ if ( $listdivider.data("line") === false ) {
+ this.options.listDividerLine = false;
+ }
+
+ if ( $listdivider.data("folded") === true ) {
+ this.options.folded = true;
+ }
+
+ if ( style == undefined || style === "normal" || style === "check" ) {
+ if ( this.options.folded ) {
+ $listdivider.buttonMarkup();
+ } else {
+ $listdivider.wrapInner("<span class='ui-btn-text'></span>");
+ }
+
+ if ( this.options.listDividerLine ) {
+ expandSrc = "<span class='ui-divider-normal-line'></span>";
+ if ( this.options.folded ) {
+ $( expandSrc ).appendTo( $listdivider.children( ".ui-btn-inner" ) );
+ } else {
+ $( expandSrc ).appendTo( $listdivider);
+ }
+ }
+ }
+
+ $listdivider.bind( "vclick", function ( event, ui ) {
+ /* need to implement expand/collapse divider */
+ });
+ }
+ });
+
+ //auto self-init widgets
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $( $.tizen.listdivider.prototype.options.initSelector, e.target ).listdivider();
+ });
+}( jQuery ) );
+
+
+
+/*
+ * Dual licensed under the MIT (http://www.opensource.org/licenses/mit-license.php) and GPL licenses
+ * http://phpjs.org/functions/range
+ * original by: Waldo Malqui Silva
+ * version: 1107.2516
+ */
+function range( low, high, step ) {
+ // Create an array containing the range of integers or characters
+ // from low to high (inclusive)
+ //
+ // version: 1107.2516
+ // discuss at: http://phpjs.org/functions/range
+ // + original by: Waldo Malqui Silva
+ // * example 1: range ( 0, 12 );
+ // * returns 1: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]
+ // * example 2: range( 0, 100, 10 );
+ // * returns 2: [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100]
+ // * example 3: range( 'a', 'i' );
+ // * returns 3: ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i']
+ // * example 4: range( 'c', 'a' );
+ // * returns 4: ['c', 'b', 'a']
+ var matrix = [],
+ inival,
+ endval,
+ plus,
+ walker = step || 1,
+ chars = false;
+
+ if (!isNaN(low) && !isNaN(high)) {
+ inival = low;
+ endval = high;
+ } else if (isNaN(low) && isNaN(high)) {
+ chars = true;
+ inival = low.charCodeAt(0);
+ endval = high.charCodeAt(0);
+ } else {
+ inival = (isNaN(low) ? 0 : low);
+ endval = (isNaN(high) ? 0 : high);
+ }
+
+ plus = ((inival > endval) ? false : true);
+ if (plus) {
+ while (inival <= endval) {
+ matrix.push(((chars) ? String.fromCharCode(inival) : inival));
+ inival += walker;
+ }
+ } else {
+ while (inival >= endval) {
+ matrix.push(((chars) ? String.fromCharCode(inival) : inival));
+ inival -= walker;
+ }
+ }
+
+ return matrix;
+}
+
+
+
+
+/* ***************************************************************************
+ Flora License
+
+ Version 1.1, April, 2013
+
+ http://floralicense.org/license/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and
+ all other entities that control, are controlled by, or are
+ under common control with that entity. For the purposes of
+ this definition, "control" means (i) the power, direct or indirect,
+ to cause the direction or management of such entity,
+ whether by contract or otherwise, or (ii) ownership of fifty percent (50%)
+ or more of the outstanding shares, or (iii) beneficial ownership of
+ such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation source,
+ and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or Object form,
+ made available under the License, as indicated by a copyright notice
+ that is included in or attached to the work (an example is provided
+ in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object form,
+ that is based on (or derived from) the Work and for which the editorial
+ revisions, annotations, elaborations, or other modifications represent,
+ as a whole, an original work of authorship. For the purposes of this License,
+ Derivative Works shall not include works that remain separable from,
+ or merely link (or bind by name) to the interfaces of, the Work and
+ Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including the original
+ version of the Work and any modifications or additions to that Work or
+ Derivative Works thereof, that is intentionally submitted to Licensor
+ for inclusion in the Work by the copyright owner or by an individual or
+ Legal Entity authorized to submit on behalf of the copyright owner.
+ For the purposes of this definition, "submitted" means any form of
+ electronic, verbal, or written communication sent to the Licensor or
+ its representatives, including but not limited to communication on
+ electronic mailing lists, source code control systems, and issue
+ tracking systems that are managed by, or on behalf of, the Licensor
+ for the purpose of discussing and improving the Work, but excluding
+ communication that is conspicuously marked or otherwise designated
+ in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ "Tizen Certified Platform" shall mean a software platform that complies
+ with the standards set forth in the Tizen Compliance Specification
+ and passes the Tizen Compliance Tests as defined from time to time
+ by the Tizen Technical Steering Group and certified by the Tizen
+ Association or its designated agent.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work
+ solely as incorporated into a Tizen Certified Platform, where such
+ license applies only to those patent claims licensable by such
+ Contributor that are necessarily infringed by their Contribution(s)
+ alone or by combination of their Contribution(s) with the Work solely
+ as incorporated into a Tizen Certified Platform to which such
+ Contribution(s) was submitted. If You institute patent litigation
+ against any entity (including a cross-claim or counterclaim
+ in a lawsuit) alleging that the Work or a Contribution incorporated
+ within the Work constitutes direct or contributory patent infringement,
+ then any patent licenses granted to You under this License for that
+ Work shall terminate as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof pursuant to the copyright license
+ above, in any medium, with or without modifications, and in Source or
+ Object form, provided that You meet the following conditions:
+
+ 1. You must give any other recipients of the Work or Derivative Works
+ a copy of this License; and
+ 2. You must cause any modified files to carry prominent notices stating
+ that You changed the files; and
+ 3. You must retain, in the Source form of any Derivative Works that
+ You distribute, all copyright, patent, trademark, and attribution
+ notices from the Source form of the Work, excluding those notices
+ that do not pertain to any part of the Derivative Works; and
+ 4. If the Work includes a "NOTICE" text file as part of its distribution,
+ then any Derivative Works that You distribute must include a readable
+ copy of the attribution notices contained within such NOTICE file,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works, in at least one of the following places:
+ within a NOTICE text file distributed as part of the Derivative Works;
+ within the Source form or documentation, if provided along with the
+ Derivative Works; or, within a display generated by the Derivative Works,
+ if and wherever such third-party notices normally appear.
+ The contents of the NOTICE file are for informational purposes only
+ and do not modify the License.
+
+ You may add Your own attribution notices within Derivative Works
+ that You distribute, alongside or as an addendum to the NOTICE text
+ from the Work, provided that such additional attribution notices
+ cannot be construed as modifying the License. You may add Your own
+ copyright statement to Your modifications and may provide additional or
+ different license terms and conditions for use, reproduction, or
+ distribution of Your modifications, or for any such Derivative Works
+ as a whole, provided Your use, reproduction, and distribution of
+ the Work otherwise complies with the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
- var $listdivider = this.element,
- openStatus = true,
- expandSrc,
- listDividerLine = true,
- style = $listdivider.attr( "data-style" );
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
- if ( $listdivider.data("line") === false ) {
- this.options.listDividerLine = false;
- }
+ END OF TERMS AND CONDITIONS
- if ( $listdivider.data("folded") === true ) {
- this.options.folded = true;
- }
+ APPENDIX: How to apply the Flora License to your work
- if ( style == undefined || style === "normal" || style === "check" ) {
- if ( this.options.folded ) {
- $listdivider.buttonMarkup();
- } else {
- $listdivider.wrapInner("<span class='ui-btn-text'></span>");
- }
+ To apply the Flora License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
- if ( this.options.listDividerLine ) {
- expandSrc = "<span class='ui-divider-normal-line'></span>";
- if ( this.options.folded ) {
- $( expandSrc ).appendTo( $listdivider.children( ".ui-btn-inner" ) );
- } else {
- $( expandSrc ).appendTo( $listdivider);
- }
- }
- }
+ Copyright [yyyy] [name of copyright owner]
- $listdivider.bind( "vclick", function ( event, ui ) {
- /* need to implement expand/collapse divider */
- });
- }
- });
+ Licensed under the Flora License, Version 1.1 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
- //auto self-init widgets
- $( document ).bind( "pagecreate create", function ( e ) {
- $( $.tizen.listdivider.prototype.options.initSelector, e.target ).listdivider();
- });
-}( jQuery ) );
+ http://floralicense.org/license/
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Authors: Yonghwi Park <yonghwi0324.park@samsung.com>
- * Wonseop Kim <wonseop.kim@samsung.com>
-*/
+ * Authors: Hyunsook Park <hyunsook.park@samsung.com>
+ * Wonseop Kim <wonseop.kim@samsung.com>
+ */
/**
+ * The gallery3d widget displays images along a curved path on a 3-dimensional coordinate system.
+ * To improve performance, the size of image(s) displayed on the screen should be a square(under
+ * 128X128 pixel) as possible. But if a user can't resize the images, this widget supports an image
+ * resizing feature and he/she can use it with "data-thumbnail-cache" option. ("data-thumbnail-cache"
+ * option resizes the gallery images under 128x128 pixels and stores the images on a local storage.
+ * So when a gallery3D widget is re-launched, the widget reuse the storage and a user can improve
+ * launching time. A browser or web runtime engine should support "Web Storage" feature to use that
+ * option.)
*
- * MultiMediaView is a widget that lets the user view and handle multimedia contents.
- * Video and audio elements are coded as standard HTML elements and enhanced by the
- * MultiMediaview to make them attractive and usable on a mobile device.
- *
- * HTML Attributes:
- * data-theme : Set a theme of widget.
- * If this value is not defined, widget will use parent`s theme. (optional)
- * data-controls : If this value is 'true', widget will use belonging controller.
- * If this value is 'false', widget will use browser`s controller.
- * Default value is 'true'.
- * data-full-screen : Set a status that full-screen when inital start.
- * Default value is 'false'.
+ * HTML Attributes:
*
- * APIs:
- * width( [number] )
- * : Get or set the width of widget.
- * The first argument is the width of widget.
- * If no first argument is specified, will act as a getter.
- * height( [number] )
- * : Get or set the height of widget.
- * The first argument is the height of widget.
- * If no first argument is specified, will act as a getter.
- * fullScreen( [boolean] )
- * : Get or Set the status of full-screen.
- * If no first argument is specified, will act as a getter.
+ * data-thumbnail-cache : Determines whether to cache and resize images.
*
- * Events:
+ * APIs:
*
- * N/A
+ * next ( void )
+ * : This method moves each image forward one by one.
+ * prev ( void )
+ * : This method moves each image backward one by one.
+ * select ( [number] )
+ * : When the "select" method is called with an argument, the method selects the image of given index.
+ * If the method is called with no argument, it will return the Javascript object having "src"
+ * attribute having the selected image's URL.
+ * add ( object or string [, number] )
+ * This method adds an image to Gallery3D widget.
+ * If the second argument isn't inputted, the image is added at the 0th position.
+ * remove ( [number] )
+ * : This method deletes an image from Gallery3d widget.
+ * The argument defines the index of the image to be deleted.
+ * If an argument isn't inputted, it removes current image.
+ * clearThumbnailCache ( void )
+ * : This method clears the cache data of all images when thumbnailCache option is set as 'true'.
+ * refresh ( void )
+ * : This method updates and redraws current widget.
+ * empty ( void )
+ * : This method removes all of images from Gallery3D widget.
+ * length ( void )
+ * : This method gets the number of images.
*
- * Examples:
+ * Events:
*
- * VIDEO :
- * <video data-controls="true" style="width:100%;">
- * <source src="media/oceans-clip.mp4" type="video/mp4" />
- * Your browser does not support the video tag.
- * </video>
+ * select : Triggered when an image is selected.
*
- * AUDIO :
- * <audio data-controls="true" style="width:100%;">
- * <source src="media/Over the horizon.mp3" type="audio/mp3" />
- * Your browser does not support the audio tag.
- * </audio>
+ * Examples:
*
+ * <script>
+ * $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ * $( "#gallery3d" ).gallery3d( "add", "01.jpg" );
+ * });
+ * </script>
+ * <div id="gallery3d" data-role="gallery3d"></div>
*/
+
+/**
+ @class Gallery3D
+ The gallery3d widget displays images along a curved path on a 3-dimensional coordinate system.
+ <br/><br/>To add an gallery3d widget to the application, use the following code:
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", "01.jpg" );
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
+*/
+/**
+ @property {Boolean} data-thumbnail-cache
+ Determines whether to cache and resize images.
+ To improve performance, the size of image(s) displayed on the screen should be a square (under 128X128 pixels).
+ "data-thumbnail-cache" option resizes the gallery images under 128x128 pixels and stores the images on a local storage.
+ So when a gallery3D widget is re-launched, the widget reuses the storage and the launching time can be improved.
+ A browser or web runtime engine must support "Web Storage" feature to use this option.
+*/
+/**
+ @event select
+ Triggered when an image is selected.
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } );
+ }).on( "select", function ( event, data, index ) {
+ // Handle the select event
+ var urlOfImage = data.src, indexOfImage = index;
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
+*/
+/**
+ @method next
+ This method moves each image forward one by one.
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } )
+ .gallery3d( "next" );
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
+*/
+/**
+ @method prev
+ This method moves each image backward one by one.
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } )
+ .gallery3d( "prev" );
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
+*/
/**
- @class MutimediaView
- The multimedia view widget shows a player control that you can use to view and handle multimedia content. This widget uses the standard HTML video and audio elements, which have been enhanced for use on a mobile device.
+ @method select
+ When the "select" method is called with an argument, the method selects the image of given index.
+ If the method is called with no argument, it will return the Javascript object having "src" attribute having the selected image's URL.
- To add a multimedia view widget to the application, use the following code:
-
- // Video player control
- <video data-controls="true" style="width:100%;">
- <source src="<VIDEO_FILE_URL>" type="video/mp4" /> Your browser does not support the video tag. </video>
- // Audio player control
- <audio data-controls="true" style="width:100%;"> <source src="<AUDIO_FILE_URL>" type="audio/mp3" /> Your browser does not support the audio tag.
- </audio>
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } );
+ var selectedImage = $("#gallery3d"). gallery3d( "select" );
+ // selectedImage = { src: "3.jpg" };
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
*/
/**
- @property {Boolean} data-control
- Sets the controls for the widget.
- The default value is true. If the value is set to true, the widget uses its own player controls. If the value is set to false, the widget uses the browser's player controls.
+ @method add
+ This method adds an image to Gallery3D widget.
+ The first argument is a Javascript object having a "src" attribute or a string of image's path.
+ The second argument is an index of images.
+ If second argument isn't inputted, the image is added at the 0th position.
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", "2.jpg", 1 );
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
*/
/**
- @property {Boolean} data-full-screen
- Defines whether the widget opens in the fullscreen view mode.
- The default value is false.
+ @method remove
+ This method deletes an image from Gallery3d widget.
+ The argument defines the index of the image to be deleted.
+ If an argument isn't inputted, it removes current image.
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } );
+
+ $( "#gallery3d" ).gallery3d( "remove" );
+ $( "#gallery3d" ).gallery3d( "remove", 1 );
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
*/
/**
- @property {String} data-theme
- Sets the widget theme.
- If the value is not set, the parent control's theme is used
+ @method clearThumbnailCache
+ This method clears the cache data of all images when thumbnailCache option is set as 'true'
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } );
+
+ $( "#gallery3d" ).gallery3d( "clearThumbnailCache" );
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d" data-thumbnail-cache="true"></div>
*/
/**
- @method width
- The width method is used to get (if no value is defined) or set the multimedia view widget width:
- <video>
- <source src="test.mp4" type="video/mp4" />
- </video>
- $(".selector").multimediaview("width", [value]);
+ @method refresh
+ This method updates and redraws current widget.
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } );
+
+ $( "#gallery3d" ).gallery3d( "refresh" );
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
*/
/**
- @method height
- The height method is used to get (if no value is defined) or set the multimedia view widget height:
- <video>
- <source src="test.mp4" type="video/mp4" />
- </video>
- $(".selector").multimediaview("height", [value]);
+ @method empty
+ This method removes all of images from Gallery3D widget.
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } );
+
+ $( "#gallery3d" ).gallery3d( "empty" );
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
*/
/**
- @method fullScreen
- The fullScreen method is used to get (if no value is defined) or set the full-screen mode of the multimedia view widget. If the value is true, the full-screen mode is used; otherwise the multimedia view widget runs in the normal mode.
+ @method length
+ This method gets the number of images.
+
+ <script>
+ $( "#gallery3d" ).on( "gallery3dcreate", function () {
+ $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
+ .gallery3d( "add", { src: "2.jpg" } )
+ .gallery3d( "add", { src: "3.jpg" } );
+
+ var imagesLength = $( "#gallery3d" ).gallery3d( "length" );
+ // imagesLength = 3;
+ });
+ </script>
+ <div id="gallery3d" data-role="gallery3d"></div>
+*/
+
+( function ( $, document, window, undefined ) {
+ function Node() {
+ this.vertices = [
+ -1.0, -1.0, 0.0,
+ 1.0, -1.0, 0.0,
+ 1.0, 1.0, 0.0,
+ -1.0, 1.0, 0.0
+ ];
+ this.textureCoords = [
+ 1.0, 0.0,
+ 0.0, 0.0,
+ 0.0, 1.0,
+ 1.0, 1.0
+ ];
+ this.normalVectors = [
+ 0.0, 0.0, 1.0,
+ 0.0, 0.0, 1.0,
+ 0.0, 0.0, 1.0,
+ 0.0, 0.0, 1.0
+ ];
+ this.texture = null;
+ this.textureBuffer = null;
+ this.textureBufferItemSize = 0;
+ this.mashOrder = [];
+ this.mvMatrix = null;
+ this.level = -1;
+ this.targetLevel = 0;
+ this.drawable = false;
+ this.image = null;
+ this.imageID = 0;
+ }
+
+ var isPreInitailization = false,
+ glMatrix = {},
+ VERTEX_SHADER,
+ FRAGMENT_SHADER,
+ GlArray32,
+ GlArray16,
+ preInitialize = function () {
+ if ( isPreInitailization ) {
+ return;
+ }
+
+ window.initGlMatrix( glMatrix );
+
+ VERTEX_SHADER = [
+ "attribute vec3 aVertexPosition;",
+ "attribute vec2 aTextureCoord;",
+ "attribute vec3 aVertexNormal;",
+ "uniform mat4 uMoveMatrix;",
+ "uniform mat4 uPerspectiveMatrix;",
+ "uniform mat3 nNormalMatrix;",
+ "uniform vec3 uAmbientColor;",
+ "uniform vec3 uLightDirection;",
+ "uniform vec3 uDirectionColor;",
+ "uniform vec3 uLightDirection_first;",
+ "uniform vec3 uLightDirection_second;",
+ "varying vec2 vTextureCoord;",
+ "varying vec3 vLightWeight;",
+ "varying vec4 vFogWeight;",
+
+ "void main(void) {",
+ " vec4 v_Position = uMoveMatrix * vec4(aVertexPosition, 1.0);",
+ " gl_Position = uPerspectiveMatrix * v_Position;",
+ " vTextureCoord = aTextureCoord;",
+ " float fog = 1.0 - ((gl_Position.z + 1.5) / 60.0);",
+ " vFogWeight = clamp( vec4( fog, fog, fog, 1.0), 0.6, 1.0);",
+ " vec3 transNormalVector = nNormalMatrix * aVertexNormal;",
+
+ " float vLightWeightFirst = 0.0;",
+ " float vLightWeightSecond = max( dot(transNormalVector, uLightDirection_second), 0.0 );",
+
+ " vLightWeight = uAmbientColor + uDirectionColor * vLightWeightSecond;",
+ "}"
+ ].join( "\n" );
+
+ FRAGMENT_SHADER = [
+ "precision mediump float;",
+ "varying vec2 vTextureCoord;",
+ "varying vec3 vLightWeight;",
+ "uniform sampler2D uSampler;",
+ "varying vec4 vFogWeight;",
+
+ "void main(void) {",
+ " vec4 TextureColor;",
+ " if ( vTextureCoord.s <= 0.01 || vTextureCoord.s >= 0.99 || vTextureCoord.t <= 0.01 || vTextureCoord.t >= 0.99 ) {",
+ " TextureColor = vec4(1.0, 1.0, 1.0, 0.5);",
+ " } else {",
+ " TextureColor = texture2D(uSampler, vec2(vTextureCoord.s, vTextureCoord.t));",
+ " }",
+ " TextureColor *= vFogWeight;",
+ " gl_FragColor = vec4(TextureColor.rgb * vLightWeight, TextureColor.a);",
+ "}"
+ ].join( "\n" );
+
+ GlArray32 = ( typeof window.Float32Array !== "undefined" ?
+ window.Float32Array :
+ ( typeof window.WebGLFloatArray !== "undefined" ? window.WebGLFloatArray : Array ) );
+
+ GlArray16 = ( typeof window.Uint16Array !== "undefined" ? window.Uint16Array : Array );
+
+ isPreInitailization = true;
+ },
+ degreeToRadian = function ( degree ) {
+ return degree * Math.PI / 180;
+ },
+ getContext3D = function ( canvas ) {
+ var gl, i,
+ contextNames = [ "experimental-webgl", "webkit-3d", "webgl", "moz-webgl" ];
+
+ for ( i = 0; i < contextNames.length; i += 1 ) {
+ try {
+ gl = canvas.getContext( contextNames[i] );
+ if ( gl ) {
+ break;
+ }
+ } catch ( e ) {
+ $( canvas ).html( "Unfortunately, there's a WebGL compatibility problem. </br> You may want to check your system settings." );
+ return;
+ }
+ }
+ return gl;
+ },
+ requestAnimationFrame = function ( callback ) {
+ var id = window.setTimeout( callback, 1000 / 60 );
+ return id;
+ },
+ cancelAnimationFrame = function ( id ) {
+ window.clearTimeout( id );
+ };
- <video>
- <source src="test.mp4" type="video/mp4" />
- </video>
- $(".selector").multimediaview("fullScreen", [value]);
-*/
-( function ( $, document, window, undefined ) {
- $.widget( "tizen.multimediaview", $.mobile.widget, {
+ $.widget( "tizen.gallery3d", $.mobile.widget, {
options: {
- theme: null,
- controls: true,
- fullScreen: false,
- initSelector: "video, audio"
+ thumbnailCache: false
},
+ _MAX_ITEM_COUNT: 28,
+ _ANIMATION_END: 999,
+ _DURATION_DEFAULT: 300,
+ _DURATION_FIRST: 1600,
+ _VIEWPORT_WIDTH: 1024,
+ _VIEWPORT_HEIGHT: 456,
+ _DIRECTION_LEFT: -1,
+ _DIRECTION_RIGHT: +1,
+
+ _gl: null,
+ _shaderProgram : null,
+ _positionBuffer : null,
+ _textureCoordBuffer : null,
+ _normalVectorBuffer : null,
+ _nodes: null,
+ _pMatrix : null,
+ _animationID: 0,
+ _dragInterval : 0,
+ _startTime : 0,
+ _sumTime : 0,
+ _lightsPositionStack : [
+ [0.0, 0.0, -1.0], // back
+ [-0.2, 0.0, 0.7] // front
+ ],
+ _path: null,
+ _swipeThresholdOfBasetimeGap: ( $.support.touch ? 30 : 70 ),
+ _swipeThresholdOfSensitivity: ( $.support.touch ? 2.0 : 10.0 ),
+ _canvas: null,
+ _imageList: [],
+ _maxDrawLength: 0,
+ _firstImageNumber: 0,
+ _lastImageNumber: 0,
+
_create: function () {
var self = this,
view = self.element,
- viewElement = view[0],
- isVideo = ( viewElement.nodeName === "VIDEO" ),
- option = self.options,
- parentTheme = $.mobile.getInheritedTheme( view, "s" ),
- theme = option.theme || parentTheme,
- width = viewElement.style.getPropertyValue( "width" ) || "",
- wrap = $( "<div class='ui-multimediaview-wrap ui-multimediaview-" + theme + "'>" ),
- control = null;
-
- $.extend( this, {
- role: null,
- controlTimer: null,
- isVolumeHide: true,
- backupView: null,
- _reserveVolume: -1,
- _isVideo: isVideo
- });
-
- view.addClass( "ui-multimediaview" );
- control = self._createControl();
- control.hide();
+ option = self.options;
- control.find( ".ui-button" ).each( function ( index ) {
- $( this ).buttonMarkup( { corners: true, theme: theme, shadow: true } );
- });
+ preInitialize();
- view.wrap( wrap ).after( control );
+ self._canvas = $( "<canvas class='ui-gallery3d-canvas'></canvas>" );
- if ( isVideo ) {
- control.addClass( "ui-multimediaview-video" );
- } else {
- self.width( width );
- self.options.fullScreen = false;
- }
+ view.addClass( "ui-gallery3d" ).append( self._canvas );
+ self._addBehavier();
- if ( option.controls && view.attr( "controls" ) ) {
- view.removeAttr( "controls" );
- }
+ self._dragInterval = 1000 / 30; // 30fps
- self._addEvent();
+ $.each( self.options, function ( key, value ) {
+ self.options[ key ] = undefined;
+ self._setOption( key, value );
+ });
},
- _resize: function () {
- this._resizeFullscreen( this.options.fullScreen );
- this._resizeControl();
- this._updateSeekBar();
- this._updateVolumeState();
+ destroy: function () {
+ this._final();
+ $.mobile.widget.prototype.destroy.call( this );
},
- _resizeControl: function () {
- var self = this,
- view = self.element,
- viewElement = view[0],
- isVideo = self._isVideo,
- wrap = view.parent( ".ui-multimediaview-wrap" ),
- control = wrap.find( ".ui-multimediaview-control" ),
- buttons = control.find( ".ui-button" ),
- playpauseButton = control.find( ".ui-playpausebutton" ),
- seekBar = control.find( ".ui-seekbar" ),
- durationLabel = control.find( ".ui-durationlabel" ),
- timestampLabel = control.find( ".ui-timestamplabel" ),
- volumeControl = control.find( ".ui-volumecontrol" ),
- volumeBar = volumeControl.find( ".ui-volumebar" ),
- width = ( isVideo ? view.width() : wrap.width() ),
- height = ( isVideo ? view.height() : control.height() ),
- offset = view.offset(),
- controlHeight = control.height(),
- availableWidth = 0,
- controlOffset = null;
-
- if ( control ) {
- if ( isVideo ) {
- controlOffset = control.offset();
- controlOffset.left = offset.left;
- controlOffset.top = offset.top + height - controlHeight;
- control.offset( controlOffset );
+ _setOption: function ( key, value ) {
+ switch ( key ) {
+ case "thumbnailCache" :
+ if ( typeof value === "string" ) {
+ value = ( value === "true" ) ? true : false;
+ } else {
+ value = !!value;
}
- control.width( width );
+ this._reset();
+ break;
}
- if ( seekBar ) {
- availableWidth = control.width() - ( buttons.outerWidth( true ) * buttons.length );
- availableWidth -= ( parseInt( buttons.eq( 0 ).css( "margin-left" ), 10 ) + parseInt( buttons.eq( 0 ).css( "margin-right" ), 10 ) ) * buttons.length;
- if ( !self.isVolumeHide ) {
- availableWidth -= volumeControl.outerWidth( true );
- }
- seekBar.width( availableWidth );
- }
+ $.mobile.widget.prototype._setOption.call( this, key, value );
+ },
- if ( durationLabel && !isNaN( viewElement.duration ) ) {
- durationLabel.find( "p" ).text( self._convertTimeFormat( viewElement.duration ) );
- }
+ _init: function ( canvas ) {
+ var self = this,
+ pathPoints = [
+ [40, 0, -48],
+ [-12, 0, -40], // contorl Point of Point1
+ [24, 0, -9], // contorl Point of Point2
+ [-5, 0, -5]
+ ],
+ i;
- if ( viewElement.autoplay && viewElement.paused === false ) {
- playpauseButton.removeClass( "ui-play-icon" ).addClass( "ui-pause-icon" );
- }
+ canvas = canvas || self._canvas;
- if ( seekBar.width() < ( volumeBar.width() + timestampLabel.width() + durationLabel.width() ) ) {
- durationLabel.hide();
- } else {
- durationLabel.show();
+ if ( !canvas ) {
+ return;
}
- },
- _resizeFullscreen: function ( isFullscreen ) {
- if ( !this._isVideo ) {
+ self._gl = self._gl || self._initGL( canvas[0] );
+ if ( !self._gl ) {
return;
}
- var self = this,
- view = self.element,
- viewElement = view[0],
- wrap = view.parent( ".ui-multimediaview-wrap" ),
- control = wrap.find( ".ui-multimediaview-control" ),
- fullscreenButton = control.find( ".ui-fullscreenbutton" ),
- currentPage = $( ".ui-page-active" ),
- playpauseButton = control.find( ".ui-playpausebutton" ),
- timestampLabel = control.find( ".ui-timestamplabel" ),
- seekBar = control.find( ".ui-seekbar" ),
- durationBar = seekBar.find( ".ui-duration" ),
- currenttimeBar = seekBar.find( ".ui-currenttime" ),
- body = $( "body" )[0],
- header = currentPage.children( ".ui-header" ),
- footer = currentPage.children( ".ui-footer" ),
- docWidth = 0,
- docHeight = 0;
-
- if ( isFullscreen ) {
- if ( !self.backupView ) {
- self.backupView = {
- width: viewElement.style.getPropertyValue( "width" ) || "",
- height: viewElement.style.getPropertyValue( "height" ) || "",
- position: view.css( "position" ),
- zindex: view.css( "z-index" ),
- wrapHeight: wrap[0].style.getPropertyValue( "height" ) || ""
- };
- }
- docWidth = body.clientWidth;
- docHeight = body.clientHeight - 1;
-
- header.hide();
- footer.hide();
- view.parents().each( function ( e ) {
- var element = $( this );
- element.addClass( "ui-fullscreen-parents" )
- .siblings()
- .addClass( "ui-multimediaview-siblings-off" );
- });
- fullscreenButton.removeClass( "ui-fullscreen-on" ).addClass( "ui-fullscreen-off" );
+ if ( !self._imageList ) {
+ return;
+ }
- wrap.height( docHeight );
- view.width( docWidth ).height( docHeight );
- } else {
- if ( !self.backupView ) {
- return;
- }
+ self._shaderProgram = self._shaderProgram || self._initShader( self._gl );
+ if ( !self._shaderProgram ) {
+ return;
+ }
- header.show();
- footer.show();
- view.parents().each( function ( e ) {
- var element = $( this );
- element.removeClass( "ui-fullscreen-parents" )
- .siblings()
- .removeClass( "ui-multimediaview-siblings-off" );
- });
+ if ( self._imageList.length > self._MAX_ITEM_COUNT ) {
+ self._firstImageNumber = self._imageList.length - 1;
+ self._lastImageNumber = self._MAX_ITEM_COUNT - 1;
+ }
- fullscreenButton.removeClass( "ui-fullscreen-off" ).addClass( "ui-fullscreen-on" );
+ self._nodes = self._initBuffers( self._gl, self._shaderProgram );
- wrap.css( "height", self.backupView.wrapHeight );
- view.css( {
- "width": self.backupView.width,
- "height": self.backupView.height,
- "position": self.backupView.position,
- "z-index": self.backupView.zindex
- });
- self.backupView = null;
+ self._initTextures( self._gl, self._nodes );
- $( window ).trigger( "throttledresize" );
+ self._path = $.motionpath( "bezier2d", {
+ points: pathPoints,
+ maxLevel: self._MAX_ITEM_COUNT
+ } );
+ for ( i = 0; i < self._nodes.length; i += 1 ) {
+ self._path.levels[i] = self._path.levels[i + 1] || 0;
+ self._nodes[i].level = i;
}
},
- _addEvent: function () {
+ _final: function ( canvas ) {
var self = this,
- view = self.element,
- option = self.options,
- viewElement = view[0],
- isVideo = self._isVideo,
- control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
- playpauseButton = control.find( ".ui-playpausebutton" ),
- timestampLabel = control.find( ".ui-timestamplabel" ),
- durationLabel = control.find( ".ui-durationlabel" ),
- volumeButton = control.find( ".ui-volumebutton" ),
- volumeControl = control.find( ".ui-volumecontrol" ),
- volumeBar = volumeControl.find( ".ui-volumebar" ),
- volumeGuide = volumeControl.find( ".ui-guide" ),
- volumeHandle = volumeControl.find( ".ui-handle" ),
- fullscreenButton = control.find( ".ui-fullscreenbutton" ),
- seekBar = control.find( ".ui-seekbar" ),
- durationBar = seekBar.find( ".ui-duration" ),
- currenttimeBar = seekBar.find( ".ui-currenttime" ),
- $document = $( document );
+ gl = self._gl;
- view.bind( "loadedmetadata.multimediaview", function ( e ) {
- if ( !isNaN( viewElement.duration ) ) {
- durationLabel.find( "p" ).text( self._convertTimeFormat( viewElement.duration ) );
- }
- self._resize();
- }).bind( "timeupdate.multimediaview", function ( e ) {
- self._updateSeekBar();
- }).bind( "play.multimediaview", function ( e ) {
- playpauseButton.removeClass( "ui-play-icon" ).addClass( "ui-pause-icon" );
- }).bind( "pause.multimediaview", function ( e ) {
- playpauseButton.removeClass( "ui-pause-icon" ).addClass( "ui-play-icon" );
- }).bind( "ended.multimediaview", function ( e ) {
- if ( typeof viewElement.loop == "undefined" || viewElement.loop === "" ) {
- self.stop();
- }
- }).bind( "volumechange.multimediaview", function ( e ) {
- if ( viewElement.muted && viewElement.volume > 0.1 ) {
- volumeButton.removeClass( "ui-volume-icon" ).addClass( "ui-mute-icon" );
- self._reserveVolume = viewElement.volume;
- viewElement.volume = 0;
- } else if ( self._reserveVolume !== -1 && !viewElement.muted ) {
- volumeButton.removeClass( "ui-mute-icon" ).addClass( "ui-volume-icon" );
- viewElement.volume = self._reserveVolume;
- self._reserveVolume = -1;
- } else if ( viewElement.volume < 0.1 ) {
- volumeButton.removeClass( "ui-volume-icon" ).addClass( "ui-mute-icon" );
- } else {
- volumeButton.removeClass( "ui-mute-icon" ).addClass( "ui-volume-icon" );
- }
+ if ( !gl ) {
+ return;
+ }
- if ( !self.isVolumeHide ) {
- self._updateVolumeState();
- }
- }).bind( "durationchange.multimediaview", function ( e ) {
- if ( !isNaN( viewElement.duration ) ) {
- durationLabel.find( "p" ).text( self._convertTimeFormat( viewElement.duration ) );
- }
- self._resize();
- }).bind( "click.multimediaview", function ( e ) {
- if ( !self.options.controls ) {
- return;
- }
+ self._stop();
- control.fadeToggle( "fast" );
- self._resize();
- }).bind( "multimediaviewinit", function ( e ) {
- if ( option.controls ) {
- control.show();
- }
- self._resize();
+ canvas = canvas || self._canvas;
+
+ $( self._nodes ).each( function ( i ) {
+ var node = self._nodes[i];
+ gl.deleteTexture( node.texture );
+ node.texture = null;
});
+ self._nodes = null;
- playpauseButton.bind( "click.multimediaview", function () {
- self._endTimer();
+ gl.deleteBuffer( self._positionBuffer );
+ self._positionBuffer = null;
+ gl.deleteBuffer( self._textureCoordBuffer );
+ self._textureCoordBuffer = null;
+ gl.deleteBuffer( self._normalVectorBuffer );
+ self._normalVectorBuffer = null;
- if ( viewElement.paused ) {
- viewElement.play();
- } else {
- viewElement.pause();
- }
+ $.webgl.shader.deleteShaders( gl );
+ gl.deleteProgram( self._shaderProgram );
+ self._shaderProgram = null;
- if ( isVideo ) {
- self._startTimer();
- }
- });
+ self._gl = gl = null;
+ },
- fullscreenButton.bind( "click.multimediaview", function ( e ) {
+ _addBehavier : function () {
+ var self = this,
+ view = self.element,
+ canvas = self._canvas,
+ touchStartEvt = ( $.support.touch ? "touchstart" : "mousedown" ),
+ touchMoveEvt = ( $.support.touch ? "touchmove" : "mousemove" ) + ".gallery3d",
+ touchEndEvt = ( $.support.touch ? "touchend" : "mouseup" ) + ".gallery3d",
+ touchLeaveEvt = ( $.support.touch ? "touchleave" : "mouseout" ) + ".gallery3d";
+
+ canvas.on( "webglcontextlost", function ( e ) {
e.preventDefault();
- self.fullScreen( !self.options.fullScreen );
- self._resize();
- self._endTimer();
- e.stopPropagation();
- });
+ }).on( "webglcontextrestored", function ( e ) {
+ self._init();
+ }).on( touchStartEvt, function ( e ) {
+ var i = 0,
+ startX = 0,
+ deltaMaxSteps = 20,
+ deltas = [ deltaMaxSteps ],
+ deltaTimes = [ deltaMaxSteps ],
+ deltaIndex = 0,
+ dragValue = 0,
+ dragDirection = false,
+ prevTime = 0;
- seekBar.bind( "vmousedown.multimediaview", function ( e ) {
- var x = e.clientX,
- duration = viewElement.duration,
- durationOffset = durationBar.offset(),
- durationWidth = durationBar.width(),
- timerate = ( x - durationOffset.left ) / durationWidth,
- time = duration * timerate;
+ e.preventDefault();
+ e.stopPropagation();
- if ( !viewElement.played.length ) {
+ if ( self._imageList.length <= 1 ) {
return;
}
- viewElement.currentTime = time;
+ self._stop();
- self._endTimer();
+ startX = $.support.touch ? e.originalEvent.changedTouches[0].pageX : e.pageX;
+ prevTime = $.now();
- e.preventDefault();
+ for ( i = 0; i < deltaMaxSteps; i += 1 ) {
+ deltas[i] = startX;
+ deltaTimes[i] = $.now();
+ }
- $document.bind( "vmousemove.multimediaview", function ( e ) {
- var x = e.clientX,
- timerate = ( x - durationOffset.left ) / durationWidth;
+ deltaIndex += 1;
- viewElement.currentTime = duration * timerate;
+ view.on( touchMoveEvt, function ( e ) {
+ var x, dx, interval;
e.preventDefault();
- }).bind( "vmouseup.multimediaview", function () {
- $document.unbind( "vmousemove.multimediaview vmouseup.multimediaview" );
- if ( viewElement.paused ) {
- viewElement.pause();
- } else {
- viewElement.play();
- }
- });
- });
+ e.stopPropagation();
- volumeButton.bind( "click.multimediaview", function () {
- if ( self.isVolumeHide ) {
- var view = self.element,
- volume = viewElement.volume;
+ x = $.support.touch ? e.originalEvent.changedTouches[0].pageX : e.pageX;
+ dx = startX - x;
- self.isVolumeHide = false;
- volumeControl.fadeIn( "fast", function () {
- self._updateVolumeState();
- self._updateSeekBar();
- });
- self._resize();
- } else {
- self.isVolumeHide = true;
- volumeControl.fadeOut( "fast", function () {
- self._resize();
- });
- }
- });
+ deltas[deltaIndex] = x;
+ deltaTimes[deltaIndex] = $.now();
+ interval = deltaTimes[deltaIndex] - prevTime;
- volumeBar.bind( "vmousedown.multimediaview", function ( e ) {
- var baseX = e.clientX,
- volumeGuideLeft = volumeGuide.offset().left,
- volumeGuideWidth = volumeGuide.width(),
- volumeBase = volumeGuideLeft + volumeGuideWidth,
- handlerOffset = volumeHandle.offset(),
- volumerate = ( baseX - volumeGuideLeft ) / volumeGuideWidth,
- currentVolume = ( baseX - volumeGuideLeft ) / volumeGuideWidth;
+ deltaIndex = ( deltaIndex + 1 ) % deltaMaxSteps;
- self._endTimer();
- self._setVolume( currentVolume.toFixed( 2 ) );
+ // Validation of drag
+ if ( Math.abs( dx ) >= 10 && interval >= self._dragInterval ) {
+ if ( dragDirection !== ( ( dx < 0 ) ? self._DIRECTION_RIGHT : self._DIRECTION_LEFT ) ) {
+ dragValue = 0;
+ dragDirection = ( dx < 0 ) ? self._DIRECTION_RIGHT : self._DIRECTION_LEFT;
+ }
- e.preventDefault();
+ dragValue += Math.abs( dx ) / 100;
+ if ( dragValue >= 1 ) {
+ self._setPosition( self._ANIMATION_END, dragDirection );
+ dragValue = 0;
+ } else {
+ self._setPosition( dragValue, dragDirection );
+ }
+ self._drawScene();
+ startX = x;
+ prevTime = $.now();
+ }
+ }).on( touchEndEvt, function ( e ) {
+ var baseTime = 0,
+ recent = -1,
+ index = 0,
+ previous = 0,
+ baseTimeRatio = 0,
+ fx = 0,
+ lastX = 0,
+ velocityX = 0,
+ dx = 0,
+ isSwipe = true,
+ direction;
+
+ e.preventDefault();
+ e.stopPropagation();
+
+ // Validation of swipe
+ baseTime = $.now() - self._swipeThresholdOfBasetimeGap;
+ lastX = $.support.touch ? e.originalEvent.changedTouches[0].pageX : e.pageX;
+ dx = startX - lastX;
+ startX = 0;
+ for ( i = 0; i < deltaMaxSteps; i += 1 ) {
+ index = ( deltaIndex + i ) % deltaMaxSteps;
+ if ( deltaTimes[index] > baseTime ) {
+ recent = index;
+ break;
+ }
+ }
+ if ( recent < 0 ) {
+ isSwipe = false;
+ }
+
+ if ( isSwipe ) {
+ previous = recent;
+ for ( i = 0; i < deltaMaxSteps; i += 1 ) {
+ previous = ( previous - 1 + deltaMaxSteps ) % deltaMaxSteps;
+ if ( deltaTimes[previous] < deltaTimes[recent] ) {
+ break;
+ }
+ }
+ // too slow or too fast
+ if ( i === deltaMaxSteps || baseTime < deltaTimes[previous] ) {
+ isSwipe = false;
+ }
+ }
- $document.bind( "vmousemove.multimediaview", function ( e ) {
- var currentX = e.clientX,
- currentVolume = ( currentX - volumeGuideLeft ) / volumeGuideWidth;
+ if ( isSwipe ) {
+ baseTimeRatio = ( baseTime - deltaTimes[previous] ) / ( deltaTimes[recent] - deltaTimes[previous] );
+ fx = ( 1.0 - baseTimeRatio ) * deltas[previous] + baseTimeRatio * deltas[recent];
+ if ( Math.abs( fx - lastX ) < self._swipeThresholdOfSensitivity ) {
+ fx = lastX;
+ }
+ velocityX = parseInt( ( lastX - fx ) / ( $.now() - baseTime ), 10 );
+ }
- self._setVolume( currentVolume.toFixed( 2 ) );
+ if ( isSwipe && velocityX ) {
+ direction = ( velocityX < 0 ) ? self._DIRECTION_LEFT : self._DIRECTION_RIGHT;
+ self._run( direction, Math.abs( velocityX ), dragValue );
+ } else if ( dragDirection !== 0 && dragValue ) {
+ self._animate( null, self._DURATION_DEFAULT * ( 1 - dragValue ), dragDirection, 0, dragValue );
+ }
- e.preventDefault();
- }).bind( "vmouseup.multimediaview", function () {
- $document.unbind( "vmousemove.multimediaview vmouseup.multimediaview" );
+ view.unbind( ".gallery3d" );
+ }).on( touchLeaveEvt, function ( e ) {
+ view.trigger( touchEndEvt );
});
});
},
- _removeEvent: function () {
- var view = this.element,
- control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
- playpauseButton = control.find( ".ui-playpausebutton" ),
- fullscreenButton = control.find( ".ui-fullscreenbutton" ),
- seekBar = control.find( ".ui-seekbar" ),
- volumeControl = control.find( ".ui-volumecontrol" ),
- volumeBar = volumeControl.find( ".ui-volumebar" ),
- volumeHandle = volumeControl.find( ".ui-handle" );
-
- view.unbind( ".multimediaview" );
- playpauseButton.unbind( ".multimediaview" );
- fullscreenButton.unbind( ".multimediaview" );
- seekBar.unbind( ".multimediaview" );
- volumeBar.unbind( ".multimediaview" );
- volumeHandle.unbind( ".multimediaview" );
- },
+ // ----------------------------------------------------------
+ // WebGL
+ // ----------------------------------------------------------
+ _initGL: function ( canvas ) {
+ var self = this,
+ mat4 = glMatrix.mat4,
+ gl;
- _createControl: function () {
- var view = this.element,
- viewElement = view[0],
- control = $( "<span></span>" ).addClass( "ui-multimediaview-control" ),
- playpauseButton = $( "<span></span>" ).addClass( "ui-playpausebutton ui-button ui-play-icon" ),
- seekBar = $( "<span></span>" ).addClass( "ui-seekbar ui-multimediaview-bar" ),
- timestampLabel = $( "<span><p>00:00:00</p></span>" ).addClass( "ui-timestamplabel" ),
- durationLabel = $( "<span><p>00:00:00</p></span>" ).addClass( "ui-durationlabel" ),
- volumeButton = $( "<span></span>" ).addClass( "ui-volumebutton ui-button" ),
- volumeControl = $( "<span></span>" ).addClass( "ui-volumecontrol" ),
- volumeBar = $( "<div></div>" ).addClass( "ui-volumebar ui-multimediaview-bar" ),
- volumeGuide = $( "<span></span>" ).addClass( "ui-guide ui-multimediaview-bar-bg" ),
- volumeValue = $( "<span></span>" ).addClass( "ui-value ui-multimediaview-bar-highlight" ),
- volumeHandle = $( "<span></span>" ).addClass( "ui-handle" ),
- fullscreenButton = $( "<span></span>" ).addClass( "ui-fullscreenbutton ui-button" ),
- durationBar = $( "<span></span>" ).addClass( "ui-duration ui-multimediaview-bar-bg" ),
- currenttimeBar = $( "<span></span>" ).addClass( "ui-currenttime ui-multimediaview-bar-highlight" );
+ gl = getContext3D( canvas );
+ if ( !gl ) {
+ return null;
+ }
- seekBar.append( durationBar ).append( currenttimeBar ).append( durationLabel ).append( timestampLabel );
+ gl.enable( gl.BLEND );
+ gl.blendFunc( gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA );
- volumeButton.addClass( viewElement.muted ? "ui-mute-icon" : "ui-volume-icon" );
- volumeBar.append( volumeGuide ).append( volumeValue ).append( volumeHandle );
- volumeControl.append( volumeBar );
+ gl.enable( gl.DEPTH_TEST );
+ gl.depthFunc( gl.LEQUAL );
- control.append( playpauseButton ).append( seekBar ).append( volumeControl ).append( volumeButton );
+ canvas.width = self._VIEWPORT_WIDTH;
+ canvas.height = self._VIEWPORT_HEIGHT;
+ gl.viewportWidth = canvas.width;
+ gl.viewportHeight = canvas.height;
+ gl.viewport( 0, 0, gl.viewportWidth, gl.viewportHeight );
+ self._pMatrix = mat4.create();
+ mat4.perspective( 40, gl.viewportWidth / gl.viewportHeight, 0.1, 10000.0, self._pMatrix );
- if ( this._isVideo ) {
- $( fullscreenButton ).addClass( "ui-fullscreen-on" );
- control.append( fullscreenButton );
- }
- volumeControl.hide();
+ gl.clearColor( 0.15, 0.15, 0.15, 1.0 );
+ gl.clear( gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT );
- return control;
+ return gl;
},
- _startTimer: function ( duration ) {
- this._endTimer();
-
- if ( !duration ) {
- duration = 3000;
- }
-
+ _initShader : function ( gl ) {
var self = this,
- view = self.element,
- control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
- volumeControl = control.find( ".ui-volumecontrol" );
+ shaderProgram;
- self.controlTimer = setTimeout( function () {
- self.isVolumeHide = true;
- self.controlTimer = null;
- volumeControl.hide();
- control.fadeOut( "fast" );
- }, duration );
- },
+ shaderProgram = $.webgl.shader.addShaderProgram( self._gl, VERTEX_SHADER, FRAGMENT_SHADER );
+ gl.useProgram( shaderProgram );
- _endTimer: function () {
- if ( this.controlTimer ) {
- clearTimeout( this.controlTimer );
- this.controlTimer = null;
- }
- },
+ shaderProgram.vertexPositionAttr = gl.getAttribLocation( shaderProgram, "aVertexPosition" );
+ gl.enableVertexAttribArray( shaderProgram.vertexPositionAttr );
- _convertTimeFormat: function ( systime ) {
- if ( !$.isNumeric( systime ) ) {
- return "Playback Error";
- }
+ shaderProgram.textureCoordAttr = gl.getAttribLocation( shaderProgram, "aTextureCoord" );
+ gl.enableVertexAttribArray( shaderProgram.textureCoordAttr );
- var ss = parseInt( systime % 60, 10 ).toString(),
- mm = parseInt( ( systime / 60 ) % 60, 10 ).toString(),
- hh = parseInt( systime / 3600, 10 ).toString(),
- time = ( ( hh.length < 2 ) ? "0" + hh : hh ) + ":" +
- ( ( mm.length < 2 ) ? "0" + mm : mm ) + ":" +
- ( ( ss.length < 2 ) ? "0" + ss : ss );
+ // Set light normal vectors for lighting~
+ shaderProgram.vertexNormalAttr = gl.getAttribLocation( shaderProgram, "aVertexNormal" );
+ gl.enableVertexAttribArray( shaderProgram.vertexNormalAttr );
- return time;
- },
+ shaderProgram.perspectiveMU = gl.getUniformLocation( shaderProgram, "uPerspectiveMatrix");
+ shaderProgram.transformMU = gl.getUniformLocation( shaderProgram, "uMoveMatrix");
+ shaderProgram.sampleUniform = gl.getUniformLocation( shaderProgram, "uSampler");
- _updateSeekBar: function ( currenttime ) {
- var view = this.element,
- viewElement = view[0],
- duration = viewElement.duration,
- control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
- seekBar = control.find( ".ui-seekbar" ),
- durationBar = seekBar.find( ".ui-duration" ),
- currenttimeBar = seekBar.find( ".ui-currenttime" ),
- timestampLabel = control.find( ".ui-timestamplabel" ),
- durationOffset = durationBar.offset(),
- durationWidth = durationBar.width(),
- durationHeight = durationBar.height(),
- timebarWidth = 0;
+ // Set light variables~
+ shaderProgram.normalMU = gl.getUniformLocation( shaderProgram, "nNormalMatrix");
+ shaderProgram.ambientColorU = gl.getUniformLocation( shaderProgram, "uAmbientColor");
+ shaderProgram.lightDirU_first = gl.getUniformLocation( shaderProgram, "uLightDirection_first");
+ shaderProgram.lightDirU_second = gl.getUniformLocation( shaderProgram, "uLightDirection_second");
+ shaderProgram.directionColorU = gl.getUniformLocation( shaderProgram, "uDirectionColor");
- if ( typeof currenttime === "undefined" ) {
- currenttime = viewElement.currentTime;
- }
- timebarWidth = parseInt( currenttime / duration * durationWidth, 10 );
- durationBar.offset( durationOffset );
- currenttimeBar.offset( durationOffset ).width( timebarWidth );
- timestampLabel.find( "p" ).text( this._convertTimeFormat( currenttime ) );
+ return shaderProgram;
},
- _updateVolumeState: function () {
- var view = this.element,
- control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
- volumeControl = control.find( ".ui-volumecontrol" ),
- volumeButton = control.find( ".ui-volumebutton" ),
- volumeBar = volumeControl.find( ".ui-volumebar" ),
- volumeGuide = volumeControl.find( ".ui-guide" ),
- volumeValue = volumeControl.find( ".ui-value" ),
- volumeHandle = volumeControl.find( ".ui-handle" ),
- handlerWidth = volumeHandle.width(),
- handlerHeight = volumeHandle.height(),
- volumeGuideHeight = volumeGuide.height(),
- volumeGuideWidth = volumeGuide.width(),
- volumeGuideTop = 0,
- volumeGuideLeft = 0,
- volumeBase = 0,
- handlerOffset = null,
- volume = view[0].volume;
-
- volumeGuideTop = parseInt( volumeGuide.offset().top, 10 );
- volumeGuideLeft = parseInt( volumeGuide.offset().left, 10 );
- volumeBase = volumeGuideLeft;
- handlerOffset = volumeHandle.offset();
- handlerOffset.top = volumeGuideTop - parseInt( ( handlerHeight - volumeGuideHeight ) / 2, 10 );
- handlerOffset.left = volumeBase + parseInt( volumeGuideWidth * volume, 10 ) - parseInt( handlerWidth / 2, 10 );
- volumeHandle.offset( handlerOffset );
- volumeValue.offset( volumeGuide.offset() ).width( parseInt( volumeGuideWidth * ( volume ), 10 ) );
- },
+ _initBuffers: function ( gl, shaderProgram ) {
+ var self = this,
+ i = 0,
+ mashBase = 0,
+ vertices = [],
+ textureCoords = [],
+ normalVectors = [],
+ nodes = [],
+ maxDrawLength = self._MAX_ITEM_COUNT;
- _setVolume: function ( value ) {
- var viewElement = this.element[0];
+ for ( i = 0; i < self._imageList.length + 1; i += 1 ) {
+ nodes[i] = new Node();
+ $.merge( vertices, nodes[i].vertices );
+ $.merge( textureCoords, nodes[i].textureCoords );
+ $.merge( normalVectors, nodes[i].normalVectors );
- if ( value < 0.0 || value > 1.0 ) {
- return;
+ nodes[i].textureBuffer = gl.createBuffer();
+ gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, nodes[i].textureBuffer );
+ mashBase = i * 4;
+ nodes[i].meshOrder = [
+ mashBase, mashBase + 1, mashBase + 2,
+ mashBase + 2, mashBase + 3, mashBase
+ ];
+ gl.bufferData( gl.ELEMENT_ARRAY_BUFFER, new GlArray16( nodes[i].meshOrder ), gl.STATIC_DRAW );
+ gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, null ); // release buffer memory
+ nodes[i].textureBufferItemSize = 6;
}
- viewElement.volume = value;
- },
+ self._positionBuffer = $.webgl.buffer.attribBufferData( gl, new GlArray32( vertices ) );
+ self._positionBuffer.itemSize = 3;
- width: function ( value ) {
- if ( this.options.fullScreen ) {
- return;
- }
+ self._textureCoordBuffer = $.webgl.buffer.attribBufferData( gl, new GlArray32( textureCoords ) );
+ self._textureCoordBuffer.itemSize = 2;
+
+ self._normalVectorBuffer = $.webgl.buffer.attribBufferData( gl, new GlArray32( normalVectors ) ); // Vertex's normal vector for Direction light
+ self._normalVectorBuffer.itemSize = 3;
+
+ // Ambient light
+ gl.uniform3f( shaderProgram.ambientColorU, 0.1, 0.1, 0.1 );
+ // Direcntion light
+ gl.uniform3f( shaderProgram.directionColorU, 1.0, 1.0, 1.0 );
- var view = this.element,
- wrap = view.parent( ".ui-multimediaview-wrap" );
+ return nodes;
+ },
- if ( arguments.length === 0 ) {
- return view.width();
- }
+ // ----------------------------------------------------------
+ // Texture
+ // ----------------------------------------------------------
+ _initTextures: function ( gl, nodes ) {
+ var self = this;
- if ( !this._isVideo ) {
- wrap.width( value );
- }
+ $( nodes ).each( function ( i ) {
+ var node = nodes[i],
+ url;
- view.width( value );
- this._resize();
+ if ( !self._imageList[i] ) {
+ return false;
+ }
+
+ url = self._imageList[i].src;
+ node.texture = gl.createTexture();
+ self._loadImage( url, i, i, gl, nodes );
+ });
},
- height: function ( value ) {
- if ( !this._isVideo || this.options.fullScreen ) {
- return;
- }
+ _loadImage: function ( url, i, imageID, gl, nodes ) {
+ var self = this,
+ isMipmap = false,
+ image,
+ node;
- var view = this.element;
+ gl = gl || self._gl;
+ nodes = nodes || self._nodes;
+ isMipmap = isMipmap || false;
+ node = nodes[i];
+ node.image = node.image || new Image();
- if ( arguments.length === 0 ) {
- return view.height();
- }
+ $( node.image ).one( "load", function ( e ) {
+ self._bindTexture( gl, node, this, isMipmap );
+ node.imageID = imageID;
- view.height( value );
- this._resize();
+ if ( !self._animationID ) {
+ self._setPosition( 0, 0 );
+ }
+ });
+
+ if ( self.options.thumbnailCache ) {
+ $.imageloader.getThumbnail( url, function ( result ) {
+ if ( result === "NOT_FOUND_ERR" ) {
+ $.imageloader.setThumbnail( url, function ( result ) {
+ if ( result && result.length > 30 ) {
+ node.image.src = result;
+ isMipmap = true;
+ } else {
+ node.image.src = url;
+ }
+ });
+ } else if ( result && result.length > 30 ) {
+ node.image.src = result;
+ isMipmap = true;
+ } else {
+ node.image.src = url;
+ }
+ });
+ } else {
+ node.image.src = url;
+ }
},
- fullScreen: function ( value ) {
- if ( !this._isVideo ) {
+ _bindTexture: function ( gl, node, image, isMipmap ) {
+ if ( !node || !node.texture ) {
return;
}
- var view = this.element,
- option = this.options;
+ gl.pixelStorei( gl.UNPACK_FLIP_Y_WEBGL, true );
- if ( arguments.length === 0 ) {
- return option.fullScreen;
+ gl.bindTexture( gl.TEXTURE_2D, node.texture );
+ gl.texImage2D( gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, image );
+
+ if ( isMipmap ) {
+ gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR );
+ gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR_MIPMAP_NEAREST );
+ gl.generateMipmap( gl.TEXTURE_2D );
+ } else {
+ gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR );
+ gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR );
}
- view.parents( ".ui-scrollview-clip" ).scrollview( "scrollTo", 0, 0 );
+ gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE );
+ gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE );
- this.options.fullScreen = value;
+ node.texture.loaded = true;
- this._resize();
+ // release texture memory
+ gl.bindTexture( gl.TEXTURE_2D, null );
},
- refresh: function () {
- this._resize();
- }
- });
+ // ----------------------------------------------------------
+ // rendering
+ // ----------------------------------------------------------
+ _setPosition: function ( progress, direction ) {
+ var self = this,
+ mat4 = glMatrix.mat4,
+ nodes = self._nodes,
+ imageList = self._imageList,
+ imageListLength = imageList.length,
+ itemCount = self._MAX_ITEM_COUNT,
+ displayLength = ( imageListLength > itemCount ) ? itemCount : imageListLength,
+ nextLevelLenth = 0,
+ i = 0,
+ t = 0,
+ position = 0,
+ angle = 0,
+ current = 0,
+ next = 0,
+ nextLevel = 0,
+ path = self._path,
+ nextImageID = 0;
- $( document ).bind( "pagecreate create", function ( e ) {
- $.tizen.multimediaview.prototype.enhanceWithin( e.target );
- }).bind( "pagechange", function ( e ) {
- $( e.target ).find( ".ui-multimediaview" ).each( function () {
- var view = $( this ),
- viewElement = view[0];
+ nextLevelLenth = ( direction >= 0 ) ? displayLength + 1 : displayLength;
- if ( viewElement.autoplay ) {
- viewElement.play();
+ if ( !nodes[i].level ) {
+ nodes[i].level = displayLength;
}
- view.multimediaview( "refresh" );
- });
- }).bind( "pagebeforechange", function ( e ) {
- $( e.target ).find( ".ui-multimediaview" ).each( function () {
- var view = $( this ),
- viewElement = view[0],
- isFullscreen = view.multimediaview( "fullScreen" );
- if ( isFullscreen ) {
- view.multimediaview( "fullScreen", !isFullscreen );
- }
+ for ( i = 0; i < displayLength; i += 1 ) {
+ if ( !nodes[i].mvMatrix ) {
+ nodes[i].mvMatrix = mat4.create();
+ }
- if ( viewElement.played.length !== 0 ) {
- viewElement.pause();
- }
- });
- });
+ if ( direction > 0 && nodes[i].level >= displayLength ) {
+ nodes[i].level = 0;
+ }
- $( window ).bind( "resize orientationchange", function ( e ) {
- $( ".ui-page-active" ).find( ".ui-multimediaview" ).multimediaview( "refresh" );
- });
+ current = path.levels[nodes[i].level];
+ nextLevel = ( nodes[i].level + nextLevelLenth + direction ) % nextLevelLenth;
+ next = path.levels[nextLevel];
-} ( jQuery, document, window ) );
+ if ( imageListLength > itemCount ) {
+ if ( direction > 0 && nextLevel === 1
+ && self._firstImageNumber !== nodes[i].imageID ) {
+ self._loadImage( imageList[self._firstImageNumber].src, i, self._firstImageNumber );
+ } else if ( direction < 0 && nextLevel === nextLevelLenth - 1
+ && self._lastImageNumber !== nodes[i].imageID ) {
+ self._loadImage( imageList[self._lastImageNumber].src, i, self._lastImageNumber );
+ }
+ }
+ mat4.identity( nodes[i].mvMatrix );
+ mat4.translate( nodes[i].mvMatrix, [-2.0, -2.0, 1.0] );
+ mat4.rotate( nodes[i].mvMatrix, degreeToRadian( 19 ), [1, 0, 0] );
+ t = ( current + ( next - current ) * ( ( progress > 1 ) ? 1 : progress ) );
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software" ),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- */
+ if ( progress >= self._ANIMATION_END ) {
+ nodes[i].level = nextLevel || displayLength;
+ t = path.levels[nodes[i].level];
+ }
-// most of following codes are derived from jquery.mobile.scrollview.js
-(function ( $, window, document, undefined ) {
+ if ( ( progress < self._ANIMATION_END )
+ && ( direction <= 0 && nodes[i].level < 1 ) ) {
+ nodes[i].drawable = false;
+ } else {
+ nodes[i].drawable = true;
+ }
- function circularNum( num, total ) {
- var n = num % total;
- if ( n < 0 ) {
- n = total + n;
- }
- return n;
- }
+ if ( progress === self._ANIMATION_END && nodes[i].level === 1 ) {
+ self.element.trigger( "select", imageList[ nodes[i].imageID ], nodes[i].imageID );
+ }
- function setElementTransform( $ele, x, y ) {
- var v = "translate3d( " + x + "," + y + ", 0px)";
- $ele.css({
- "-ms-transform": v,
- "-o-transform": v,
- "-moz-transform": v,
- "-webkit-transform": v,
- "transform": v
- } );
- }
+ position = path.getPosition( t );
+ angle = path.getAngle( t );
+
+ mat4.translate( nodes[i].mvMatrix, position );
+ mat4.rotate( nodes[i].mvMatrix, angle, [0, 1, 0] );
+ }
+
+ if ( imageListLength > itemCount && progress >= self._ANIMATION_END ) {
+ self._firstImageNumber = ( self._firstImageNumber - direction ) % imageListLength;
+ if ( self._firstImageNumber < 0 ) {
+ self._firstImageNumber = imageListLength - 1;
+ }
+
+ self._lastImageNumber = ( self._lastImageNumber - direction ) % imageListLength;
+ if ( self._lastImageNumber < 0 ) {
+ self._lastImageNumber = imageListLength - 1;
+ }
+ }
+ self._drawScene();
+ },
- function MomentumTracker( options ) {
- this.options = $.extend( {}, options );
- this.easing = "easeOutQuad";
- this.reset();
- }
+ _drawScene: function () {
+ if ( !this._gl || !this._shaderProgram ) {
+ return;
+ }
- var tstates = {
- scrolling : 0,
- done : 1
- };
+ var self = this,
+ gl = self._gl,
+ shaderProgram = self._shaderProgram,
+ nodes = self._nodes,
+ nodesLength = nodes.length,
+ i;
- function getCurrentTime() {
- return Date.now();
- }
+ gl.clear( gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT );
- $.extend( MomentumTracker.prototype, {
- start: function ( pos, speed, duration ) {
- this.state = ( speed != 0 ) ? tstates.scrolling : tstates.done;
- this.pos = pos;
- this.speed = speed;
- this.duration = duration;
+ gl.bindBuffer( gl.ARRAY_BUFFER, self._positionBuffer );
+ gl.vertexAttribPointer( shaderProgram.vertexPositionAttr, self._positionBuffer.itemSize, gl.FLOAT, false, 0, 0 );
- this.fromPos = 0;
- this.toPos = 0;
+ gl.bindBuffer( gl.ARRAY_BUFFER, self._textureCoordBuffer );
+ gl.vertexAttribPointer( shaderProgram.textureCoordAttr, self._textureCoordBuffer.itemSize, gl.FLOAT, false, 0, 0 );
- this.startTime = getCurrentTime();
- },
+ gl.bindBuffer( gl.ARRAY_BUFFER, self._normalVectorBuffer );
+ gl.vertexAttribPointer( shaderProgram.vertexNormalAttr, self._normalVectorBuffer.itemSize, gl.FLOAT, false, 0, 0 );
- reset: function () {
- this.state = tstates.done;
- this.pos = 0;
- this.speed = 0;
- this.duration = 0;
+ for ( i = 0; i < nodesLength; i += 1 ) {
+ if ( nodes[i].drawable ) {
+ self._drawElement( self._pMatrix, nodes[i] );
+ }
+ }
},
- update: function () {
- var state = this.state,
- duration,
- elapsed,
- dx,
- x;
+ _drawElement: function ( perspectiveMatrix, targetNode ) {
+ var self = this,
+ gl = self._gl,
+ vec3 = glMatrix.vec3,
+ mat3 = glMatrix.mat3,
+ mat4 = glMatrix.mat4,
+ shaderProgram = self._shaderProgram,
+ moveMatrix = targetNode.mvMatrix,
+ texture = targetNode.texture,
+ meshIndexBuffer = targetNode.textureBuffer,
+ meshIndexBufferItemSize = targetNode.textureBufferItemSize,
+ lightPositions = self._lightsPositionStack,
+ LightDir,
+ normalMatrix;
- if ( state == tstates.done ) {
- return this.pos;
+ if ( !moveMatrix ) {
+ return;
}
- duration = this.duration;
- elapsed = getCurrentTime() - this.startTime;
- elapsed = elapsed > duration ? duration : elapsed;
-
- dx = this.speed * ( 1 - $.easing[this.easing](elapsed / duration, elapsed, 0, 1, duration ) );
-
- x = this.pos + dx;
- this.pos = x;
-
- if ( elapsed >= duration ) {
- this.state = tstates.done;
+ gl.activeTexture( gl.TEXTURE0 );
+ if ( texture && texture.loaded ) {
+ gl.bindTexture( gl.TEXTURE_2D, texture );
}
+ gl.uniform1i( shaderProgram.sampleUniform, 0 );
- return this.pos;
- },
+ LightDir = vec3.create();
+ vec3.normalize( lightPositions[0], LightDir );
+ vec3.scale( LightDir, -8 );
+ gl.uniform3fv( shaderProgram.lightDirU_first, LightDir );
- done: function () {
- return this.state == tstates.done;
- },
+ vec3.normalize( lightPositions[1], LightDir );
+ vec3.scale( LightDir, -1 );
+ gl.uniform3fv( shaderProgram.lightDirU_second, LightDir );
+ gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, meshIndexBuffer );
- getPosition: function () {
- return this.pos;
- }
- } );
+ gl.uniformMatrix4fv( shaderProgram.perspectiveMU, false, perspectiveMatrix );
+ gl.uniformMatrix4fv( shaderProgram.transformMU, false, moveMatrix );
- jQuery.widget( "mobile.circularview", jQuery.mobile.widget, {
- options: {
- fps: 60,
+ normalMatrix = mat3.create();
+ mat4.toInverseMat3( moveMatrix, normalMatrix );
+ mat3.transpose( normalMatrix );
+ gl.uniformMatrix3fv( shaderProgram.normalMU, false, normalMatrix );
- scrollDuration: 2000,
+ gl.drawElements( gl.TRIANGLES, meshIndexBufferItemSize, gl.UNSIGNED_SHORT, 0 );
- moveThreshold: 10,
- moveIntervalThreshold: 150,
+ // release buffer memory
+ gl.bindBuffer( gl.ARRAY_BUFFER, null );
+ gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, null );
- startEventName: "scrollstart",
- updateEventName: "scrollupdate",
- stopEventName: "scrollstop",
+ // release texture memory
+ gl.bindTexture( gl.TEXTURE_2D, null );
+ },
- eventType: $.support.touch ? "touch" : "mouse",
+ // ----------------------------------------------------------
+ // Animation
+ // ----------------------------------------------------------
+ _animate: function ( easingType, duration, direction, repeatCount, startValue, _removeCount ) {
+ var self = this,
+ timeNow = $.now(),
+ progress,
+ removeCount = 0;
- delayedClickSelector: "a, .ui-btn",
- delayedClickEnabled: false
- },
+ easingType = easingType || "linear";
+ startValue = startValue || 0;
+ _removeCount = _removeCount || 0;
- _makePositioned: function ( $ele ) {
- if ( $ele.css( 'position' ) == 'static' ) {
- $ele.css( 'position', 'relative' );
+ if ( self._sumTime >= duration ) {
+ self._setPosition( self._ANIMATION_END, direction );
+ self._stop();
+ return;
}
- },
- _create: function () {
- var self = this;
+ if ( self._startTime === 0 ) {
+ self._startTime = timeNow;
+ } else {
+ self._sumTime = timeNow - self._startTime;
+ progress = $.easing[ easingType ]( self._sumTime / duration, self._sumTime, startValue, repeatCount + 1, duration );
+ removeCount = parseInt( Math.abs( progress ), 10 );
- this._items = $( this.element ).jqmData('list');
- this._$clip = $( this.element ).addClass( "ui-scrollview-clip" );
- this._$clip.wrapInner( '<div class="ui-scrollview-view"></div>' );
- this._$view = $('.ui-scrollview-view', this._$clip );
- this._$list = $( 'ul', this._$clip );
+ if ( _removeCount !== removeCount ) {
+ self._setPosition( self._ANIMATION_END, direction );
+ _removeCount = removeCount;
- this._$clip.css( "overflow", "hidden" );
- this._makePositioned( this._$clip );
+ if ( ( repeatCount - _removeCount ) >= 0 ) {
+ self._animate( easingType, duration, direction, repeatCount, startValue, _removeCount );
+ } else {
+ self._stop();
+ }
+ return;
+ }
- this._$view.css( "overflow", "hidden" );
- this._tracker = new MomentumTracker( this.options );
+ self._setPosition( progress - _removeCount, direction );
+ }
- this._timerInterval = 1000 / this.options.fps;
- this._timerID = 0;
+ self._animationID = requestAnimationFrame( function () {
+ self._animate( easingType, duration, direction, repeatCount, startValue, _removeCount );
+ });
+ },
- this._timerCB = function () { self._handleMomentumScroll(); };
+ _run: function ( direction, repeatCount, startValue ) {
+ var self = this,
+ repeat = repeatCount || 0,
+ duration = self._DURATION_DEFAULT * ( repeat + 1 );
- this.refresh();
+ if ( self._imageList.length <= 1 ) {
+ return;
+ }
- this._addBehaviors();
- },
+ startValue = startValue || 0;
+ duration = ( duration >= 0 ) ? duration : 0;
- reflow: function () {
- var xy = this.getScrollPosition();
- this.refresh();
- this.scrollTo( xy.x, xy.y );
+ if ( self._animationID ) {
+ self._setPosition( self._ANIMATION_END, direction );
+ self._stop();
+ }
+
+ self._animate( "easeOutExpo", duration, direction, repeat, startValue );
},
- refresh: function () {
- var itemsPerView;
+ _reset: function () {
+ if ( !this._canvas || !this._gl ) {
+ return;
+ }
- this._$clip.width( $(window).width() );
- this._clipWidth = this._$clip.width();
- this._$list.empty();
- this._$list.append(this._items[0]);
- this._itemWidth = $(this._items[0]).outerWidth();
- $(this._items[0]).detach();
+ this._final();
+ this._init();
+ this.refresh();
+ },
- itemsPerView = this._clipWidth / this._itemWidth;
- itemsPerView = Math.ceil( itemsPerView * 10 ) / 10;
- this._itemsPerView = parseInt( itemsPerView, 10 );
- while ( this._itemsPerView + 1 > this._items.length ) {
- $.merge( this._items, $(this._items).clone() );
+ _stop: function () {
+ if ( this._animationID ) {
+ cancelAnimationFrame( this._animationID );
}
- this._rx = -this._itemWidth;
- this._sx = -this._itemWidth;
- this._setItems();
+ this._animationID = 0;
+
+ this._startTime = 0;
+ this._sumTime = 0;
},
- _startMScroll: function ( speedX, speedY ) {
- this._stopMScroll();
+ next: function () {
+ this._run( this._DIRECTION_LEFT , 0 );
+ },
- var keepGoing = false,
- duration = this.options.scrollDuration,
- t = this._tracker,
- c = this._clipWidth,
- v = this._viewWidth;
+ prev: function () {
+ this._run( this._DIRECTION_RIGHT, 0 );
+ },
- this._$clip.trigger( this.options.startEventName);
+ refresh: function () {
+ var view = this.element,
+ canvas = view.find( "canvas.ui-gallery3d-canvas" );
- t.start( this._rx, speedX, duration, (v > c ) ? -(v - c) : 0, 0 );
- keepGoing = !t.done();
+ if ( canvas.width() !== view.width() ) {
+ canvas.width( view.width() );
+ }
- if ( keepGoing ) {
- this._timerID = setTimeout( this._timerCB, this._timerInterval );
- } else {
- this._stopMScroll();
+ if ( !this._animationID ) {
+ this._setPosition( 0, 0 );
}
- //console.log( "startmscroll" + this._rx + "," + this._sx );
},
- _stopMScroll: function () {
- if ( this._timerID ) {
- this._$clip.trigger( this.options.stopEventName );
- clearTimeout( this._timerID );
- }
+ select: function ( index ) {
+ var nodes = this._nodes,
+ repeat,
+ i,
+ imageID,
+ object = null,
+ target = 0,
+ direction = 0;
- this._timerID = 0;
+ if ( index && this._animationID ) {
+ this._stop();
+ }
- if ( this._tracker ) {
- this._tracker.reset();
+ for ( i in nodes ) {
+ if ( nodes[i].level === 1 ) {
+ object = this._imageList[ nodes[i].imageID ];
+ imageID = nodes[i].imageID;
+ break;
+ }
}
- //console.log( "stopmscroll" + this._rx + "," + this._sx );
- },
- _handleMomentumScroll: function () {
- var keepGoing = false,
- v = this._$view,
- x = 0,
- y = 0,
- t = this._tracker;
+ if ( !index ) {
+ return object;
+ }
- if ( t ) {
- t.update();
- x = t.getPosition();
+ if ( index < 0 && index >= this._imageList.length ) {
+ return;
+ }
- keepGoing = !t.done();
+ target = index - imageID;
+ direction = ( target > 0 ) ? this._DIRECTION_LEFT
+ : ( ( target < 0 ) ? this._DIRECTION_RIGHT : 0 );
+ if ( direction ) {
+ this._run( direction, Math.abs( target ) - 1 );
+ }
+ },
+ add: function ( item, index ) {
+ if ( !item ) {
+ return;
}
- this._setScrollPosition( x, y );
- this._rx = x;
+ if ( typeof item === "string" ) {
+ item = { "src" : item };
+ }
- this._$clip.trigger( this.options.updateEventName, [ { x: x, y: y } ] );
+ index = index || 0;
+ if ( typeof index !== "number" && index < 0
+ && index >= this._imageList.length ) {
+ return;
+ }
- if ( keepGoing ) {
- this._timerID = setTimeout( this._timerCB, this._timerInterval );
- } else {
- this._stopMScroll();
+ this._imageList.splice( index, 0, item );
+ if ( this._gl ) {
+ this._reset();
}
},
- _setItems: function () {
- var i,
- $item;
+ remove: function ( index ) {
+ index = index || 0;
+ if ( typeof index !== "number" && index < 0
+ && index >= this._imageList.length ) {
+ return;
+ }
- for ( i = -1; i < this._itemsPerView + 1; i++ ) {
- $item = this._items[ circularNum( i, this._items.length ) ];
- this._$list.append( $item );
+ this._imageList.splice( index, 1 );
+ if ( this._gl ) {
+ this._reset();
}
- setElementTransform( this._$view, this._sx + "px", 0 );
- this._$view.width( this._itemWidth * ( this._itemsPerView + 2 ) );
- this._viewWidth = this._$view.width();
},
- _setScrollPosition: function ( x, y ) {
- var sx = this._sx,
- dx = x - sx,
- di = parseInt( dx / this._itemWidth, 10 ),
- i,
- idx,
- $item;
+ clearThumbnailCache: function () {
+ if ( !this._nodes || ( this._nodes.length <= 0 ) ) {
+ return;
+ }
- if ( di > 0 ) {
- for ( i = 0; i < di; i++ ) {
- this._$list.children().last().detach();
- idx = -parseInt( ( sx / this._itemWidth ) + i + 3, 10 );
- $item = this._items[ circularNum( idx, this._items.length ) ];
- this._$list.prepend( $item );
- //console.log( "di > 0 : " + idx );
- }
- } else if ( di < 0 ) {
- for ( i = 0; i > di; i-- ) {
- this._$list.children().first().detach();
- idx = this._itemsPerView - parseInt( ( sx / this._itemWidth ) + i, 10 );
- $item = this._items[ circularNum( idx, this._items.length ) ];
- this._$list.append( $item );
- //console.log( "di < 0 : " + idx );
- }
+ var i, url;
+ for ( i = 0; i < this._imageList.length; i += 1 ) {
+ url = this._imageList[i].src;
+ $.imageloader.removeThumbnail( url );
}
+ },
- this._sx += di * this._itemWidth;
+ empty: function () {
+ this._imageList = [];
+ this._reset();
+ },
- setElementTransform( this._$view, ( x - this._sx - this._itemWidth ) + "px", 0 );
+ length: function () {
+ return this._imageList.length;
+ }
+ });
- //console.log( "rx " + this._rx + "sx " + this._sx );
- },
+ $( document ).on( "pagecreate create", function ( e ) {
+ $( ":jqmData(role='gallery3d')" ).gallery3d();
+ }).on( "pagechange", function ( e ) {
+ $( e.target ).find( ".ui-gallery3d" ).gallery3d( "refresh" );
+ });
- _enableTracking: function () {
- $(document).bind( this._dragMoveEvt, this._dragMoveCB );
- $(document).bind( this._dragStopEvt, this._dragStopCB );
- },
+ $( window ).on( "resize orientationchange", function ( e ) {
+ $( ".ui-page-active" ).find( ".ui-gallery3d" ).gallery3d( "refresh" );
+ });
- _disableTracking: function () {
- $(document).unbind( this._dragMoveEvt, this._dragMoveCB );
- $(document).unbind( this._dragStopEvt, this._dragStopCB );
- },
+} ( jQuery, document, window ) );
- _getScrollHierarchy: function () {
- var svh = [],
- d;
- this._$clip.parents( '.ui-scrollview-clip' ).each( function () {
- d = $( this ).jqmData( 'circulaview' );
- if ( d ) {
- svh.unshift( d );
- }
- } );
- return svh;
- },
- centerTo: function ( selector, duration ) {
- var i,
- newX;
- for ( i = 0; i < this._items.length; i++ ) {
- if ( $( this._items[i]).is( selector ) ) {
- newX = -( i * this._itemWidth - this._clipWidth / 2 + this._itemWidth * 1.5 );
- this.scrollTo( newX + this._itemWidth, 0 );
- this.scrollTo( newX, 0, duration );
- return;
- }
- }
- },
+/*
+* jQuery Mobile Framework : scrollview plugin
+* Copyright (c) 2010 Adobe Systems Incorporated - Kin Blas (jblas@adobe.com)
+* Dual licensed under the MIT (MIT-LICENSE.txt) and GPL (GPL-LICENSE.txt) licenses.
+* Note: Code is in draft form and is subject to change
+* Modified by Koeun Choi <koeun.choi@samsung.com>
+* Modified by Minkyu Kang <mk7.kang@samsung.com>
+*/
- scrollTo: function ( x, y, duration ) {
- this._stopMScroll();
- if ( !duration ) {
- this._setScrollPosition( x, y );
- this._rx = x;
- return;
- }
+(function ( $, window, document, undefined ) {
- var self = this,
- start = getCurrentTime(),
- efunc = $.easing.easeOutQuad,
- sx = this._rx,
- sy = 0,
- dx = x - sx,
- dy = 0,
- tfunc,
- elapsed,
- ec;
+ function resizePageContentHeight( page ) {
+ var $page = $( page ),
+ $content = $page.children(".ui-content"),
+ hh = $page.children(".ui-header").outerHeight() || 0,
+ fh = $page.children(".ui-footer").outerHeight() || 0,
+ pt = parseFloat( $content.css("padding-top") ),
+ pb = parseFloat( $content.css("padding-bottom") ),
+ wh = $( window ).height();
- this._rx = x;
+ $content.height( wh - (hh + fh) - (pt + pb) );
+ }
- tfunc = function () {
- elapsed = getCurrentTime() - start;
- if ( elapsed >= duration ) {
- self._timerID = 0;
- self._setScrollPosition( x, y );
- self._$clip.trigger("scrollend");
- } else {
- ec = efunc( elapsed / duration, elapsed, 0, 1, duration );
- self._setScrollPosition( sx + ( dx * ec ), sy + ( dy * ec ) );
- self._timerID = setTimeout( tfunc, self._timerInterval );
- }
- };
+ function MomentumTracker( options ) {
+ this.options = $.extend( {}, options );
+ this.easing = "easeOutQuad";
+ this.reset();
+ }
- this._timerID = setTimeout( tfunc, this._timerInterval );
- },
+ var tstates = {
+ scrolling: 0,
+ overshot: 1,
+ snapback: 2,
+ done: 3
+ };
+
+ function getCurrentTime() {
+ return Date.now();
+ }
+
+ jQuery.widget( "tizen.scrollview", jQuery.mobile.widget, {
+ options: {
+ direction: null, // "x", "y", or null for both.
+
+ timerInterval: 10,
+ scrollDuration: 1000, // Duration of the scrolling animation in msecs.
+ overshootDuration: 250, // Duration of the overshoot animation in msecs.
+ snapbackDuration: 500, // Duration of the snapback animation in msecs.
- getScrollPosition: function () {
- return { x: -this._rx, y: 0 };
- },
+ moveThreshold: 30, // User must move this many pixels in any direction to trigger a scroll.
+ moveIntervalThreshold: 150, // Time between mousemoves must not exceed this threshold.
- _handleDragStart: function ( e, ex, ey ) {
- $.each( this._getScrollHierarchy(), function ( i, sv ) {
- sv._stopMScroll();
- } );
+ scrollMethod: "translate", // "translate", "position"
+ startEventName: "scrollstart",
+ updateEventName: "scrollupdate",
+ stopEventName: "scrollstop",
- this._stopMScroll();
+ eventType: $.support.touch ? "touch" : "mouse",
- if ( this.options.delayedClickEnabled ) {
- this._$clickEle = $( e.target ).closest( this.options.delayedClickSelector );
- }
- this._lastX = ex;
- this._lastY = ey;
- this._speedX = 0;
- this._speedY = 0;
- this._didDrag = false;
+ showScrollBars: true,
+ overshootEnable: false,
+ outerScrollEnable: false,
+ overflowEnable: true,
+ scrollJump: false
+ },
- this._lastMove = 0;
- this._enableTracking();
+ _getViewHeight: function () {
+ return this._$view.height();
+ },
- this._ox = ex;
- this._nx = this._rx;
+ _getViewWidth: function () {
+ return this._$view.width();
+ },
- if ( this.options.eventType == "mouse" || this.options.delayedClickEnabled ) {
- e.preventDefault();
+ _makePositioned: function ( $ele ) {
+ if ( $ele.css("position") === "static" ) {
+ $ele.css( "position", "relative" );
}
- //console.log( "scrollstart" + this._rx + "," + this._sx );
- e.stopPropagation();
},
- _handleDragMove: function ( e, ex, ey ) {
- this._lastMove = getCurrentTime();
-
- var dx = ex - this._lastX,
- dy = ey - this._lastY;
+ _create: function () {
+ var direction,
+ self = this;
- this._speedX = dx;
- this._speedY = 0;
+ this._$clip = $( this.element ).addClass("ui-scrollview-clip");
- this._didDrag = true;
+ if ( this._$clip.children(".ui-scrollview-view").length ) {
+ this._$view = this._$clip.children(".ui-scrollview-view");
+ } else {
+ this._$view = this._$clip.wrapInner("<div></div>").children()
+ .addClass("ui-scrollview-view");
+ }
- this._lastX = ex;
- this._lastY = ey;
+ if ( this.options.scrollMethod === "translate" ) {
+ if ( this._$view.css("transform") === undefined ) {
+ this.options.scrollMethod = "position";
+ }
+ }
- this._mx = ex - this._ox;
+ this._$clip.css( "overflow", "hidden" );
+ this._makePositioned( this._$clip );
- this._setScrollPosition( this._nx + this._mx, 0 );
+ this._makePositioned( this._$view );
+ this._$view.css( { left: 0, top: 0 } );
- //console.log( "scrollmove" + this._rx + "," + this._sx );
- return false;
- },
+ this._view_height = this._getViewHeight();
- _handleDragStop: function ( e ) {
- var l = this._lastMove,
- t = getCurrentTime(),
- doScroll = l && ( t - l ) <= this.options.moveIntervalThreshold,
- sx = ( this._tracker && this._speedX && doScroll ) ? this._speedX : 0,
- sy = 0;
+ this._sx = 0;
+ this._sy = 0;
- this._rx = this._mx ? this._nx + this._mx : this._rx;
+ direction = this.options.direction;
- if ( sx ) {
- this._startMScroll( sx, sy );
- }
+ this._hTracker = ( direction !== "y" ) ?
+ new MomentumTracker( this.options ) : null;
+ this._vTracker = ( direction !== "x" ) ?
+ new MomentumTracker( this.options ) : null;
- //console.log( "scrollstop" + this._rx + "," + this._sx );
+ this._timerInterval = this.options.timerInterval;
+ this._timerID = 0;
- this._disableTracking();
+ this._timerCB = function () {
+ self._handleMomentumScroll();
+ };
- if ( !this._didDrag && this.options.delayedClickEnabled && this._$clickEle.length ) {
- this._$clickEle
- .trigger( "mousedown" )
- .trigger( "mouseup" )
- .trigger( "click" );
- }
+ this._add_event();
+ this._add_scrollbar();
+ this._add_scroll_jump();
+ this._add_overflow_indicator();
+ },
- if ( this._didDrag ) {
- e.preventDefault();
- e.stopPropagation();
- }
+ _startMScroll: function ( speedX, speedY ) {
+ var keepGoing = false,
+ duration = this.options.scrollDuration,
+ ht = this._hTracker,
+ vt = this._vTracker,
+ c,
+ v;
- return this._didDrag ? false : undefined;
- },
+ this._$clip.trigger( this.options.startEventName );
- _addBehaviors: function () {
- var self = this;
+ if ( ht ) {
+ c = this._$clip.width();
+ v = this._getViewWidth();
- if ( this.options.eventType === "mouse" ) {
- this._dragStartEvt = "mousedown";
- this._dragStartCB = function ( e ) {
- return self._handleDragStart( e, e.clientX, e.clientY );
- };
+ if ( (( this._sx === 0 && speedX > 0 ) ||
+ ( this._sx === -(v - c) && speedX < 0 )) &&
+ v > c ) {
+ return;
+ }
- this._dragMoveEvt = "mousemove";
- this._dragMoveCB = function ( e ) {
- return self._handleDragMove( e, e.clientX, e.clientY );
- };
+ ht.start( this._sx, speedX,
+ duration, (v > c) ? -(v - c) : 0, 0 );
+ keepGoing = !ht.done();
+ }
- this._dragStopEvt = "mouseup";
- this._dragStopCB = function ( e ) {
- return self._handleDragStop( e );
- };
+ if ( vt ) {
+ c = this._$clip.height();
+ v = this._getViewHeight();
- this._$view.bind( "vclick", function (e) {
- return !self._didDrag;
- } );
+ if ( (( this._sy === 0 && speedY > 0 ) ||
+ ( this._sy === -(v - c) && speedY < 0 )) &&
+ v > c ) {
+ return;
+ }
- } else { //touch
- this._dragStartEvt = "touchstart";
- this._dragStartCB = function ( e ) {
- var t = e.originalEvent.targetTouches[0];
- return self._handleDragStart(e, t.pageX, t.pageY );
- };
+ vt.start( this._sy, speedY,
+ duration, (v > c) ? -(v - c) : 0, 0 );
+ keepGoing = keepGoing || !vt.done();
+ }
- this._dragMoveEvt = "touchmove";
- this._dragMoveCB = function ( e ) {
- var t = e.originalEvent.targetTouches[0];
- return self._handleDragMove(e, t.pageX, t.pageY );
- };
+ if ( keepGoing ) {
+ this._timerID = setTimeout( this._timerCB, this._timerInterval );
+ } else {
+ this._stopMScroll();
+ }
+ },
- this._dragStopEvt = "touchend";
- this._dragStopCB = function ( e ) {
- return self._handleDragStop( e );
- };
+ _stopMScroll: function () {
+ if ( this._timerID ) {
+ this._$clip.trigger( this.options.stopEventName );
+ clearTimeout( this._timerID );
}
- this._$view.bind( this._dragStartEvt, this._dragStartCB );
- }
- } );
+ this._timerID = 0;
- $( document ).bind( "pagecreate create", function ( e ) {
- $( $.mobile.circularview.prototype.options.initSelector, e.target ).circularview();
- } );
+ if ( this._vTracker ) {
+ this._vTracker.reset();
+ }
-}( jQuery, window, document ) ); // End Component
+ if ( this._hTracker ) {
+ this._hTracker.reset();
+ }
+ this._hideScrollBars();
+ this._hideOverflowIndicator();
+ },
+ _handleMomentumScroll: function () {
+ var keepGoing = false,
+ x = 0,
+ y = 0,
+ scroll_height = 0,
+ self = this,
+ vt = this._vTracker,
+ ht = this._hTracker;
-/*
- *
- * This software is licensed under the MIT licence (as defined by the OSI at
- * http://www.opensource.org/licenses/mit-license.php)
- *
- * ***************************************************************************
- * Copyright (C) 2011 by Intel Corporation Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- */
+ if ( this._outerScrolling ) {
+ return;
+ }
-// Add markup for labels
+ if ( vt ) {
+ vt.update( this.options.overshootEnable );
+ y = vt.getPosition();
+ keepGoing = !vt.done();
+ if ( vt.getRemained() > this.options.overshootDuration ) {
+ scroll_height = this._getViewHeight() - this._$clip.height();
-(function($, undefined) {
+ if ( !vt.isAvail() ) {
+ if ( this._speedY > 0 ) {
+ this._outerScroll( vt.getRemained() / 3, scroll_height );
+ } else {
+ this._outerScroll( y - vt.getRemained() / 3, scroll_height );
+ }
+ } else if ( vt.isMin() ) {
+ this._outerScroll( y - vt.getRemained() / 3, scroll_height );
-$(document).bind("pagecreate create", function(e) {
- $(":jqmData(role='label')", e.target).not(":jqmData(role='none'), :jqmData(role='nojs')").each(function() {
- $(this).addClass("jquery-mobile-ui-label")
- .html($("<span>", {"class": "jquery-mobile-ui-label-text"}).text($(this).text()));
- });
-});
+ } else if ( vt.isMax() ) {
+ this._outerScroll( vt.getRemained() / 3, scroll_height );
+ }
+ }
+ }
-})(jQuery);
+ if ( ht ) {
+ ht.update( this.options.overshootEnable );
+ x = ht.getPosition();
+ keepGoing = keepGoing || !ht.done();
+ }
+ this._setScrollPosition( x, y );
+ this._$clip.trigger( this.options.updateEventName,
+ [ { x: x, y: y } ] );
+ if ( keepGoing ) {
+ this._timerID = setTimeout( this._timerCB, this._timerInterval );
+ } else {
+ this._stopMScroll();
+ }
+ },
+ _setElementTransform: function ( $ele, x, y, duration ) {
+ var translate,
+ transition;
-/*
- * jQuery Mobile Widget @VERSION
- *
- * This software is licensed under the MIT licence (as defined by the OSI at
- * http://www.opensource.org/licenses/mit-license.php)
- *
- * ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- * Copyright (c) 2011 by Intel Corporation Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Authors: Elliot Smith <elliot.smith@intel.com>
- * Yonghwi Park <yonghwi0324.park@samsung.com>
- */
+ if ( !duration || duration === undefined ) {
+ transition = "none";
+ } else {
+ transition = "-webkit-transform " + duration / 1000 + "s ease-out";
+ }
-// fastscroll is a scrollview controller, which binds
-// a scrollview to a a list of short cuts; the shortcuts are built
-// from the text on dividers in the list. Clicking on a shortcut
-// instantaneously jumps the scrollview to the selected list divider;
-// mouse movements on the shortcut column move the scrollview to the
-// list divider matching the text currently under the touch; a popup
-// with the text currently under the touch is also displayed.
-//
-// To apply, add the attribute data-fastscroll="true" to a listview
-// (a <ul> or <ol> element inside a page). Alternatively, call
-// fastscroll() on an element.
-//
-// The closest element with class ui-scrollview-clip is used as the
-// scrollview to be controlled.
-//
-// If a listview has no dividers or a single divider, the widget won't
-// display.
+ if ( $.support.cssTransform3d ) {
+ translate = "translate3d(" + x + "," + y + ", 0px)";
+ } else {
+ translate = "translate(" + x + "," + y + ")";
+ }
-/**
- @class fastscroll
- The shortcut scroll widget shows a shortcut list that is bound to its parent scroll bar and respective list view. This widget is displayed as a text pop-up representing shortcuts to different list dividers in the list view. If you select a shortcut text from the shortcut scroll, the parent list view is moved to the location representing the selected shortcut.
+ $ele.css({
+ "-moz-transform": translate,
+ "-webkit-transform": translate,
+ "-ms-transform": translate,
+ "-o-transform": translate,
+ "transform": translate,
+ "-webkit-transition": transition
+ });
+ },
- To add a shortcut scroll widget to the application, use the following code:
+ _setEndEffect: function ( dir ) {
+ var scroll_height = this._getViewHeight() - this._$clip.height();
- <div class="content" data-role="content" data-scroll="y">
- <ul id="contacts" data-role="listview" data-fastscroll="true">
- <li>Anton</li>
- </ul>
- </div>
+ if ( this._softkeyboard ) {
+ if ( this._effect_dir ) {
+ this._outerScroll( -scroll_height - this._softkeyboardHeight,
+ scroll_height );
+ } else {
+ this._outerScroll( this._softkeyboardHeight, scroll_height );
+ }
+ return;
+ }
- For the shortcut scroll widget to be visible, the parent list view must have multiple list dividers.
-*/
+ if ( dir === "in" ) {
+ if ( this._endEffect ) {
+ return;
+ }
-/**
- @property {Boolean} data-fastscroll
- When set to true, creates a shortcut scroll using the HTML unordered list (<ul>) element.
-*/
-/**
- @method fastscroll
- The shortcut scroll is created for the closest list view with the ui-scrollview-clip class.
-*/
-/**
- @method indexString
- The indexString method is used to get (if no value is defined) or set the string to present the index.
+ this._endEffect = true;
+ this._setOverflowIndicator( this._effect_dir );
+ this._showOverflowIndicator();
+ } else if ( dir === "out" ) {
+ if ( !this._endEffect ) {
+ return;
+ }
- <div class="content" data-role="content" data-scroll="y">
- ul id="contacts" data-role="listview" data-fastscroll="true">
- <li data-role="list-divider">A</li>
- <li>Anton</li>
- </ul>
- </div>
+ this._endEffect = false;
+ } else {
+ this._endEffect = false;
+ this._setOverflowIndicator();
+ this._showOverflowIndicator();
+ }
+ },
- $(".selector").fastscroll( "indexString" [, indexAlphabet] );
-*/
-(function ( $, undefined ) {
+ _setCalibration: function ( x, y ) {
+ if ( this.options.overshootEnable ) {
+ this._sx = x;
+ this._sy = y;
+ return;
+ }
- $.widget( "tizen.fastscroll", $.mobile.widget, {
- options: {
- initSelector: ":jqmData(fastscroll)"
- },
+ var $v = this._$view,
+ $c = this._$clip,
+ dirLock = this._directionLock,
+ scroll_height = 0,
+ scroll_width = 0;
- _primaryLanguage: null,
- _secondLanguage: null,
- _dividerMap: {},
- _defaultTime: 500,
- _defaultDuration: 500,
- _timer: null,
- _isFadeOut: false,
+ if ( dirLock !== "y" && this._hTracker ) {
+ scroll_width = $v.width() - $c.width();
- _create: function () {
- var $el = this.element,
- self = this,
- $popup,
- page = $el.closest( ':jqmData(role="page")' ),
- jumpToDivider;
+ if ( x >= 0 ) {
+ this._sx = 0;
+ } else if ( x < -scroll_width ) {
+ this._sx = -scroll_width;
+ } else {
+ this._sx = x;
+ }
- this.scrollview = $el.closest( '.ui-scrollview-clip' );
- this.shortcutsContainer = $( '<div class="ui-fastscroll" aria-label="Fast scroll bar, double tap to fast scroll mode" tabindex="0"/>' );
- this.shortcutsList = $( '<ul aria-hidden="true"></ul>' );
+ if ( scroll_width < 0 ) {
+ this._sx = 0;
+ }
+ }
- // popup for the hovering character
- this.scrollview.append($( '<div class="ui-fastscroll-popup"></div>' ) );
- $popup = this.scrollview.find( '.ui-fastscroll-popup' );
+ if ( dirLock !== "x" && this._vTracker ) {
+ scroll_height = this._getViewHeight() - $c.height();
- this.shortcutsContainer.append( this.shortcutsList );
- this.scrollview.append( this.shortcutsContainer );
+ if ( y > 0 ) {
+ this._sy = 0;
- // find the bottom of the last item in the listview
- this.lastListItem = $el.children().last();
+ this._effect_dir = 0;
+ this._setEndEffect( "in" );
+ } else if ( y < -scroll_height ) {
+ this._sy = -scroll_height;
- // remove scrollbars from scrollview
- this.scrollview.find( '.ui-scrollbar' ).hide();
+ this._effect_dir = 1;
+ this._setEndEffect( "in" );
+ } else {
+ if ( this._endEffect && this._sy !== y ) {
+ this._setEndEffect();
+ }
- this.jumpToDivider = function ( divider ) {
- // get the vertical position of the divider (so we can scroll to it)
- var dividerY = $( divider ).position().top,
- // find the bottom of the last list item
- bottomOffset = self.lastListItem.outerHeight( true ) + self.lastListItem.position().top,
- scrollviewHeight = self.scrollview.height(),
+ this._sy = y;
+ }
- // check that after the candidate scroll, the bottom of the
- // last item will still be at the bottom of the scroll view
- // and not some way up the page
- maxScroll = bottomOffset - scrollviewHeight,
- dstOffset;
+ if ( scroll_height < 0 ) {
+ this._sy = 0;
+ }
+ }
+ },
- dividerY = ( dividerY > maxScroll ? maxScroll : dividerY );
+ _setScrollPosition: function ( x, y, duration ) {
+ var $v = this._$view,
+ sm = this.options.scrollMethod,
+ $vsb = this._$vScrollBar,
+ $hsb = this._$hScrollBar,
+ $sbt;
- // don't apply a negative scroll, as this means the
- // divider should already be visible
- dividerY = Math.max( dividerY, 0 );
+ this._setCalibration( x, y );
- // apply the scroll
- self.scrollview.scrollview( 'scrollTo', 0, -dividerY );
+ x = this._sx;
+ y = this._sy;
- dstOffset = self.scrollview.offset();
- };
+ if ( sm === "translate" ) {
+ this._setElementTransform( $v, x + "px", y + "px", duration );
+ } else {
+ $v.css( {left: x + "px", top: y + "px"} );
+ }
- this.shortcutsList
- // bind mouse over so it moves the scroller to the divider
- .bind( 'touchstart mousedown vmousedown touchmove vmousemove vmouseover', function ( e ) {
- // Get coords relative to the element
- var coords = $.mobile.tizen.targetRelativeCoordsFromEvent( e ),
- shortcutsListOffset = self.shortcutsList.offset();
+ if ( $vsb ) {
+ $sbt = $vsb.find(".ui-scrollbar-thumb");
- if ( self._isFadeOut === true ) {
- return;
- }
+ if ( sm === "translate" ) {
+ this._setElementTransform( $sbt, "0px",
+ -y / this._getViewHeight() * $sbt.parent().height() + "px",
+ duration );
+ } else {
+ $sbt.css( "top", -y / this._getViewHeight() * 100 + "%" );
+ }
+ }
- // If the element is a list item, get coordinates relative to the shortcuts list
- if ( e.target.tagName.toLowerCase() === "li" ) {
- coords.x += $( e.target ).offset().left - shortcutsListOffset.left;
- coords.y += $( e.target ).offset().top - shortcutsListOffset.top;
- }
+ if ( $hsb ) {
+ $sbt = $hsb.find(".ui-scrollbar-thumb");
- if ( e.target.tagName.toLowerCase() === "span" ) {
- coords.x += $( e.target ).parent().offset().left - shortcutsListOffset.left;
- coords.y += $( e.target ).parent().offset().top - shortcutsListOffset.top;
- }
+ if ( sm === "translate" ) {
+ this._setElementTransform( $sbt,
+ -x / $v.width() * $sbt.parent().width() + "px", "0px",
+ duration);
+ } else {
+ $sbt.css("left", -x / $v.width() * 100 + "%");
+ }
+ }
+ },
- self.shortcutsList.find( 'li' ).each( function () {
- var listItem = $( this );
- $( listItem )
- .removeClass( "ui-fastscroll-hover" )
- .removeClass( "ui-fastscroll-hover-up" )
- .removeClass( "ui-fastscroll-hover-down" );
- });
- // Hit test each list item
- self.shortcutsList.find( 'li' ).each( function () {
- var listItem = $( this ),
- l = listItem.offset().left - shortcutsListOffset.left,
- t = listItem.offset().top - shortcutsListOffset.top,
- r = l + Math.abs(listItem.outerWidth( true ) ),
- b = t + Math.abs(listItem.outerHeight( true ) ),
- unit,
- baseTop,
- baseBottom,
- omitSet,
- i;
+ _outerScroll: function ( y, scroll_height ) {
+ var self = this,
+ top = $( window ).scrollTop() - window.screenTop,
+ sy = 0,
+ duration = this.options.snapbackDuration,
+ start = getCurrentTime(),
+ tfunc;
- if ( coords.x >= l && coords.x <= r && coords.y >= t && coords.y <= b ) {
- if ( listItem.text() !== "." ) {
- self._hitItem( listItem );
- } else {
- omitSet = listItem.data( "omitSet" );
- unit = ( b - t ) / omitSet.length;
- for ( i = 0; i < omitSet.length; i++ ) {
- baseTop = t + ( i * unit );
- baseBottom = baseTop + unit;
- if ( coords.y >= baseTop && coords.y <= baseBottom ) {
- self._hitOmitItem( listItem, omitSet.charAt( i ) );
- }
- }
- }
- return false;
- }
- return true;
- } );
+ if ( !this.options.outerScrollEnable ) {
+ return;
+ }
- self._setTimer( false );
+ if ( this._$clip.jqmData("scroll") !== "y" ) {
+ return;
+ }
- e.preventDefault();
- e.stopPropagation();
- } )
- // bind mouseout of the fastscroll container to remove popup
- .bind( 'touchend mouseup vmouseup vmouseout', function () {
- $popup.hide();
- $( ".ui-fastscroll-hover" ).removeClass( "ui-fastscroll-hover" );
- $( ".ui-fastscroll-hover-first-item" ).removeClass( "ui-fastscroll-hover-first-item" );
- $( ".ui-fastscroll-hover-up" ).removeClass( "ui-fastscroll-hover-up" );
- $( ".ui-fastscroll-hover-down" ).removeClass( "ui-fastscroll-hover-down" );
- self._setTimer( true );
- } );
+ if ( this._outerScrolling ) {
+ return;
+ }
- if ( page && !( page.is( ':visible' ) ) ) {
- page.bind( 'pageshow', function () { self.refresh(); } );
+ if ( y > 0 ) {
+ sy = ( window.screenTop ? window.screenTop : -y );
+ } else if ( y < -scroll_height ) {
+ sy = -y - scroll_height;
} else {
- self.refresh();
+ return;
}
- // refresh the list when dividers are filtered out
- $el.bind( 'updatelayout', function () {
- self.refresh();
- } );
+ tfunc = function () {
+ var elapsed = getCurrentTime() - start;
- $( window ).unbind( ".fastscroll" ).bind( "resize.fastscroll", function ( e ) {
- self.refresh();
- } );
+ if ( elapsed >= duration ) {
+ window.scrollTo( 0, top + sy );
+ self._outerScrolling = undefined;
- self.scrollview.bind( "scrollstart", function ( e ) {
- self._setTimer( false );
- }).bind( "scrollstop", function ( e ) {
- self._setTimer( true );
- });
+ self._stopMScroll();
+ } else {
+ ec = $.easing.easeOutQuad( elapsed / duration,
+ elapsed, 0, 1, duration );
+
+ window.scrollTo( 0, top + ( sy * ec ) );
+ self._outerScrolling = setTimeout( tfunc, self._timerInterval );
+ }
+ };
+ this._outerScrolling = setTimeout( tfunc, self._timerInterval );
},
- _hitOmitItem: function ( listItem, text ) {
+ _scrollTo: function ( x, y, duration ) {
var self = this,
- $popup = self.scrollview.find( '.ui-fastscroll-popup' ),
- divider = self._dividerMap[ text ];
+ start = getCurrentTime(),
+ efunc = $.easing.easeOutQuad,
+ sx = this._sx,
+ sy = this._sy,
+ dx = x - sx,
+ dy = y - sy,
+ tfunc;
- if ( typeof divider !== "undefined" ) {
- self.jumpToDivider( $( divider ) );
- }
+ x = -x;
+ y = -y;
- $popup.text( text )
- .css( { marginLeft: -( $popup.width() / 2 ),
- marginTop: -( $popup.height() / 2 ),
- padding: $popup.css( "paddingTop" ) } )
- .width( $popup.height() )
- .show();
+ tfunc = function () {
+ var elapsed = getCurrentTime() - start,
+ ec;
- $( listItem ).addClass( "ui-fastscroll-hover" );
- if ( listItem.index() === 0 ) {
- $( listItem ).addClass( "ui-fastscroll-hover-first-item" );
- }
- if ( listItem.index() > 0 ) {
- $( listItem ).siblings().eq( listItem.index() - 1 ).addClass( "ui-fastscroll-hover-up" );
- }
- $( listItem ).siblings().eq( listItem.index() ).addClass( "ui-fastscroll-hover-down" );
+ if ( elapsed >= duration ) {
+ self._timerID = 0;
+ self._setScrollPosition( x, y );
+ } else {
+ ec = efunc( elapsed / duration, elapsed, 0, 1, duration );
+
+ self._setScrollPosition( sx + ( dx * ec ), sy + ( dy * ec ) );
+ self._timerID = setTimeout( tfunc, self._timerInterval );
+ }
+ };
+
+ this._timerID = setTimeout( tfunc, this._timerInterval );
},
- _hitItem: function ( listItem ) {
- var self = this,
- $popup = self.scrollview.find( '.ui-fastscroll-popup' ),
- text = listItem.text(),
- divider;
+ scrollTo: function ( x, y, duration ) {
+ this._stopMScroll();
+ this._didDrag = false;
- if ( text === "#" ) {
- divider = self._dividerMap.number;
+ if ( !duration || this.options.scrollMethod === "translate" ) {
+ this._setScrollPosition( x, y, duration );
} else {
- divider = self._dividerMap[ text ];
- }
-
- if ( typeof divider !== "undefined" ) {
- self.jumpToDivider( $( divider ) );
+ this._scrollTo( x, y, duration );
}
+ },
- $popup.text( text )
- .css( { marginLeft: -( $popup.width() / 2 ),
- marginTop: -( $popup.height() / 2 ),
- padding: $popup.css( "paddingTop" ) } )
- .width( $popup.height() )
- .show();
+ getScrollPosition: function () {
+ return { x: -this._sx, y: -this._sy };
+ },
- $( listItem ).addClass( "ui-fastscroll-hover" );
- if ( listItem.index() === 0 ) {
- $( listItem ).addClass( "ui-fastscroll-hover-first-item" );
- }
- if ( listItem.index() > 0 ) {
- $( listItem ).siblings().eq( listItem.index() - 1 ).addClass( "ui-fastscroll-hover-up" );
- }
- $( listItem ).siblings().eq( listItem.index() ).addClass( "ui-fastscroll-hover-down" );
+ skipDragging: function ( value ) {
+ this._skip_dragging = value;
},
- _focusItem: function ( listItem ) {
- var self = this,
- $popup = self.scrollview.find( '.ui-fastscroll-popup' );
+ _getScrollHierarchy: function () {
+ var svh = [],
+ d;
- listItem.focusin( function ( e ) {
- self.shortcutsList.attr( "aria-hidden", false );
- self._hitItem( listItem );
- self._setTimer( false );
- }).focusout( function ( e ) {
- self.shortcutsList.attr( "aria-hidden", true );
- $popup.hide();
- $( ".ui-fastscroll-hover" ).removeClass( "ui-fastscroll-hover" );
- $( ".ui-fastscroll-hover-first-item" ).removeClass( "ui-fastscroll-hover-first-item" );
- $( ".ui-fastscroll-hover-up" ).removeClass( "ui-fastscroll-hover-up" );
- $( ".ui-fastscroll-hover-down" ).removeClass( "ui-fastscroll-hover-down" );
- self._setTimer( true );
- });
+ this._$clip.parents( ".ui-scrollview-clip").each( function () {
+ d = $( this ).jqmData("scrollview");
+ if ( d ) {
+ svh.unshift( d );
+ }
+ } );
+ return svh;
},
- _contentHeight: function () {
- var self = this,
- $content = $( '.ui-scrollview-clip' ),
- header = null,
- footer = null,
- paddingValue = 0,
- clipSize = $( window ).height();
+ _getAncestorByDirection: function ( dir ) {
+ var svh = this._getScrollHierarchy(),
+ n = svh.length,
+ sv,
+ svdir;
- if ( $content.hasClass( "ui-content" ) ) {
- paddingValue = parseInt( $content.css( "padding-top" ), 10 );
- clipSize = clipSize - ( paddingValue || 0 );
- paddingValue = parseInt( $content.css( "padding-bottom" ), 10 );
- clipSize = clipSize - ( paddingValue || 0 );
- header = $content.siblings( ".ui-header:visible" );
- footer = $content.siblings( ".ui-footer:visible" );
+ while ( 0 < n-- ) {
+ sv = svh[n];
+ svdir = sv.options.direction;
- if ( header ) {
- if ( header.outerHeight( true ) === null ) {
- clipSize = clipSize - ( $( ".ui-header" ).outerHeight() || 0 );
- } else {
- clipSize = clipSize - header.outerHeight( true );
- }
- }
- if ( footer ) {
- clipSize = clipSize - footer.outerHeight( true );
+ if (!svdir || svdir === dir) {
+ return sv;
}
- } else {
- clipSize = $content.height();
}
- return clipSize;
+ return null;
},
- _omit: function ( numOfItems, maxNumOfItems ) {
- var maxGroupNum = parseInt( ( maxNumOfItems - 1 ) / 2, 10 ),
- numOfExtraItems = numOfItems - maxNumOfItems,
- groupPos = [],
- omitInfo = [],
- groupPosLength,
- group,
- size,
- i;
+ _handleDragStart: function ( e, ex, ey ) {
+ this._stopMScroll();
- if ( ( maxNumOfItems < 3 ) || ( numOfItems <= maxNumOfItems ) ) {
- return;
- }
+ this._didDrag = false;
+ this._skip_dragging = false;
- if ( numOfExtraItems >= maxGroupNum ) {
- size = 2;
- group = 1;
- groupPosLength = maxGroupNum;
- } else {
- size = maxNumOfItems / ( numOfExtraItems + 1 );
- group = size;
- groupPosLength = numOfExtraItems;
- }
+ var target = $( e.target ),
+ self = this,
+ $c = this._$clip,
+ svdir = this.options.direction;
- for ( i = 0; i < groupPosLength; i++ ) {
- groupPos.push( parseInt( group, 10 ) );
- group += size;
- }
+ /* should prevent the default behavior when click the button */
+ this._is_button = target.is( '.ui-btn' ) ||
+ target.is( '.ui-btn-text' ) ||
+ target.is( '.ui-btn-inner' ) ||
+ target.is( '.ui-btn-inner .ui-icon' );
- for ( i = 0; i < maxNumOfItems; i++ ) {
- omitInfo.push( 1 );
+ /* should prevent the default behavior when click the slider */
+ if ( target.parents('.ui-slider').length || target.is('.ui-slider') ) {
+ this._skip_dragging = true;
+ return;
}
- for ( i = 0; i < numOfExtraItems; i++ ) {
- omitInfo[ groupPos[ i % maxGroupNum ] ]++;
+ if ( target.is('textarea') ) {
+ target.bind( "scroll", function () {
+ self._skip_dragging = true;
+ target.unbind("scroll");
+ });
}
- return omitInfo;
- },
-
- _createDividerMap: function () {
- var self = this,
- primaryCharacterSet = self._primaryLanguage ? self._primaryLanguage.replace( /,/g, "" ) : null,
- secondCharacterSet = self._secondLanguage ? self._secondLanguage.replace( /,/g, "" ) : null,
- numberSet = "0123456789",
- dividers = self.element.find( '.ui-li-divider' ),
- map = {},
- matchToDivider,
- makeCharacterSet,
- indexChar,
- i;
-
- matchToDivider = function ( index, divider ) {
- if ( $( divider ).text() === indexChar ) {
- map[ indexChar ] = divider;
- }
- };
-
- makeCharacterSet = function ( index, divider ) {
- primaryCharacterSet += $( divider ).text();
- };
+ /*
+ * We need to prevent the default behavior to
+ * suppress accidental selection of text, etc.
+ */
+ this._is_inputbox = target.is(':input') ||
+ target.parents(':input').length > 0;
- if ( primaryCharacterSet === null ) {
- primaryCharacterSet = "";
- dividers.each( makeCharacterSet );
+ if ( this._is_inputbox ) {
+ target.one( "resize.scrollview", function () {
+ if ( ey > $c.height() ) {
+ self.scrollTo( -ex, self._sy - ey + $c.height(),
+ self.options.snapbackDuration );
+ }
+ });
}
- for ( i = 0; i < primaryCharacterSet.length; i++ ) {
- indexChar = primaryCharacterSet.charAt( i );
- dividers.each( matchToDivider );
+ if ( this.options.eventType === "mouse" && !this._is_inputbox && !this._is_button ) {
+ e.preventDefault();
}
- if ( secondCharacterSet !== null ) {
- for ( i = 0; i < secondCharacterSet.length; i++ ) {
- indexChar = secondCharacterSet.charAt( i );
- dividers.each( matchToDivider );
- }
- }
+ this._lastX = ex;
+ this._lastY = ey;
+ this._startY = ey;
+ this._doSnapBackX = false;
+ this._doSnapBackY = false;
+ this._speedX = 0;
+ this._speedY = 0;
+ this._directionLock = "";
- dividers.each( function ( index, divider ) {
- if ( numberSet.search( $( divider ).text() ) !== -1 ) {
- map.number = divider;
- return false;
- }
- });
+ this._lastMove = 0;
+ this._enableTracking();
- self._dividerMap = map;
+ this._set_scrollbar_size();
},
- _setTimer: function ( start ) {
- var self = this;
-
- if ( start === true ) {
- self._timer = setTimeout( function () {
- self._isFadeOut = true;
- self.shortcutsContainer.fadeOut( self._defaultDuration, function () {
- self._isFadeOut = false;
- });
- }, self._defaultTime );
- } else {
- if ( self._timer !== null ) {
- clearTimeout( self._timer );
- }
- self.shortcutsContainer.show();
- }
+ _propagateDragMove: function ( sv, e, ex, ey, dir ) {
+ this._hideScrollBars();
+ this._hideOverflowIndicator();
+ this._disableTracking();
+ sv._handleDragStart( e, ex, ey );
+ sv._directionLock = dir;
+ sv._didDrag = this._didDrag;
},
- indexString: function ( indexAlphabet ) {
- var self = this,
- characterSet = [];
+ _handleDragMove: function ( e, ex, ey ) {
+ if ( this._skip_dragging ) {
+ return;
+ }
- if ( typeof indexAlphabet === "undefined" ) {
- return self._primaryLanguage + ":" + self._secondLanguage;
+ if ( !this._dragging ) {
+ return;
}
- characterSet = indexAlphabet.split( ":" );
- self._primaryLanguage = characterSet[ 0 ];
- if ( characterSet.length === 2 ) {
- self._secondLanguage = characterSet[ 1 ];
+ if ( !this._is_inputbox && !this._is_button ) {
+ e.preventDefault();
}
- },
- refresh: function () {
- var self = this,
- primaryCharacterSet = self._primaryLanguage ? self._primaryLanguage.replace( /,/g, "" ) : null,
- secondCharacterSet = self._secondLanguage ? self._secondLanguage.replace( /,/g, "" ) : null,
- contentHeight = self._contentHeight(),
- shapItem = $( '<li tabindex="0" aria-label="double to move Number list"><span aria-hidden="true">#</span><span aria-label="Number"/></li>' ),
- omitIndex = 0,
- makeCharacterSet,
- makeOmitSet,
- itemHandler,
- containerHeight,
- shortcutsItems,
- shortcutItem,
- shortcutsTop,
- minClipHeight,
- maxNumOfItems,
- numOfItems,
- minHeight,
- padding,
- omitInfo,
- dividers,
- listItems,
- emptySize,
- correction,
- indexChar,
- lastIndex,
- seconds,
- height,
- size,
- i;
+ var mt = this.options.moveThreshold,
+ dx = ex - this._lastX,
+ dy = ey - this._lastY,
+ svdir = this.options.direction,
+ dir = null,
+ x,
+ y,
+ sv,
+ scope,
+ newX,
+ newY,
+ dirLock;
- makeCharacterSet = function ( index, divider ) {
- primaryCharacterSet += $( divider ).text();
- };
+ this._lastMove = getCurrentTime();
- makeOmitSet = function ( index, length ) {
- var count,
- omitSet = "";
+ if ( !this._directionLock ) {
+ x = Math.abs( dx );
+ y = Math.abs( dy );
- for ( count = 0; count < length; count++ ) {
- omitSet += primaryCharacterSet[ index + count ];
+ if ( x < mt && y < mt ) {
+ return false;
}
- return omitSet;
- };
+ if ( x < y && (x / y) < 0.5 ) {
+ dir = "y";
+ } else if ( x > y && (y / x) < 0.5 ) {
+ dir = "x";
+ }
- itemHandler = function ( e ) {
- var text = $( this ).text(),
- matchDivider = self._dividerMap[ text ];
+ if ( svdir && dir && svdir !== dir ) {
+ /*
+ * This scrollview can't handle the direction the user
+ * is attempting to scroll. Find an ancestor scrollview
+ * that can handle the request.
+ */
- if ( typeof matchDivider !== "undefined" ) {
- $( matchDivider ).next().focus();
+ sv = this._getAncestorByDirection( dir );
+ if ( sv ) {
+ this._propagateDragMove( sv, e, ex, ey, dir );
+ return false;
+ }
}
- };
- self._createDividerMap();
+ this._directionLock = svdir || (dir || "none");
+ }
- self.shortcutsList.find( 'li' ).remove();
+ newX = this._sx;
+ newY = this._sy;
+ dirLock = this._directionLock;
- // get all the dividers from the list and turn them into shortcuts
- dividers = self.element.find( '.ui-li-divider' );
+ if ( dirLock !== "y" && this._hTracker ) {
+ x = this._sx;
+ this._speedX = dx;
+ newX = x + dx;
- // get all the list items
- listItems = self.element.find('li').not('.ui-li-divider');
+ this._doSnapBackX = false;
- // only use visible dividers
- dividers = dividers.filter( ':visible' );
- listItems = listItems.filter( ':visible' );
+ scope = ( newX > 0 || newX < this._maxX );
- if ( dividers.length < 2 ) {
- self.shortcutsList.hide();
- return;
+ if ( scope && dirLock === "x" ) {
+ sv = this._getAncestorByDirection("x");
+ if ( sv ) {
+ this._setScrollPosition( newX > 0 ?
+ 0 : this._maxX, newY );
+ this._propagateDragMove( sv, e, ex, ey, dir );
+ return false;
+ }
+
+ newX = x + ( dx / 2 );
+ this._doSnapBackX = true;
+ }
}
- self.shortcutsList.show();
- self.lastListItem = listItems.last();
- self.shortcutsList.append( shapItem );
- self._focusItem( shapItem );
+ if ( dirLock !== "x" && this._vTracker ) {
+ if ( Math.abs( this._startY - ey ) < mt && dirLock !== "xy" ) {
+ return;
+ }
- if ( primaryCharacterSet === null ) {
- primaryCharacterSet = "";
- dividers.each( makeCharacterSet );
- }
+ y = this._sy;
+ this._speedY = dy;
+ newY = y + dy;
- padding = parseInt( shapItem.css( "padding" ), 10 );
- minHeight = shapItem.height() + ( padding * 2 );
- maxNumOfItems = parseInt( ( contentHeight / minHeight ) - 1, 10 );
- numOfItems = primaryCharacterSet.length;
+ this._doSnapBackY = false;
- maxNumOfItems = secondCharacterSet ? maxNumOfItems - 2 : maxNumOfItems;
+ scope = ( newY > 0 || newY < this._maxY );
- if ( maxNumOfItems < 3 ) {
- shapItem.remove();
- return;
+ if ( scope && dirLock === "y" ) {
+ sv = this._getAncestorByDirection("y");
+ if ( sv ) {
+ this._setScrollPosition( newX,
+ newY > 0 ? 0 : this._maxY );
+ this._propagateDragMove( sv, e, ex, ey, dir );
+ return false;
+ }
+
+ newY = y + ( dy / 2 );
+ this._doSnapBackY = true;
+ }
}
- omitInfo = self._omit( numOfItems, maxNumOfItems );
+ if ( this.options.overshootEnable === false ) {
+ this._doSnapBackX = false;
+ this._doSnapBackY = false;
+ }
- for ( i = 0; i < primaryCharacterSet.length; i++ ) {
- indexChar = primaryCharacterSet.charAt( i );
- shortcutItem = $( '<li tabindex="0" aria-label="double to move ' + indexChar + ' list">' + indexChar + '</li>' );
+ this._lastX = ex;
+ this._lastY = ey;
- self._focusItem( shortcutItem );
+ this._setScrollPosition( newX, newY );
- if ( typeof omitInfo !== "undefined" && omitInfo[ omitIndex ] > 1 ) {
- shortcutItem = $( '<li>.</li>' );
- shortcutItem.data( "omitSet", makeOmitSet( i, omitInfo[ omitIndex ] ) );
- i += omitInfo[ omitIndex ] - 1;
- } else {
- shortcutItem.bind( 'vclick', itemHandler );
- }
+ if ( this._didDrag === false ) {
+ this._didDrag = true;
+ this._showScrollBars();
+ this._showOverflowIndicator();
- shapItem.before( shortcutItem );
- omitIndex++;
+ this._$clip.parents(".ui-scrollview-clip").each( function () {
+ $( this ).scrollview( "skipDragging", true );
+ } );
}
+ },
- if ( secondCharacterSet !== null ) {
- lastIndex = secondCharacterSet.length - 1;
- seconds = [];
+ _handleDragStop: function ( e ) {
+ var self = this;
- seconds.push( secondCharacterSet.charAt( 0 ) );
- seconds.push( secondCharacterSet.charAt( lastIndex ) );
+ if ( this._skip_dragging ) {
+ return;
+ }
- for ( i = 0; i < seconds.length; i++ ) {
- indexChar = seconds[ i ];
- shortcutItem = $( '<li tabindex="0" aria-label="double to move ' + indexChar + ' list">' + indexChar + '</li>' );
+ var l = this._lastMove,
+ t = getCurrentTime(),
+ doScroll = (l && (t - l) <= this.options.moveIntervalThreshold),
+ sx = ( this._hTracker && this._speedX && doScroll ) ?
+ this._speedX : ( this._doSnapBackX ? 1 : 0 ),
+ sy = ( this._vTracker && this._speedY && doScroll ) ?
+ this._speedY : ( this._doSnapBackY ? 1 : 0 ),
+ svdir = this.options.direction,
+ x,
+ y;
- self._focusItem( shortcutItem );
- shortcutItem.bind( 'vclick', itemHandler );
- shapItem.before( shortcutItem );
+ if ( sx || sy ) {
+ if ( !this._setGestureScroll( sx, sy ) ) {
+ this._startMScroll( sx, sy );
}
+ } else {
+ this._hideScrollBars();
+ this._hideOverflowIndicator();
}
- containerHeight = self.shortcutsContainer.outerHeight();
- emptySize = contentHeight - containerHeight;
- shortcutsItems = self.shortcutsList.children();
- size = parseInt( emptySize / shortcutsItems.length, 10 );
- correction = emptySize - ( shortcutsItems.length * size );
+ this._disableTracking();
- if ( emptySize > 0 ) {
- shortcutsItems.each( function ( index, item ) {
- height = $( item ).height() + size;
- if ( correction !== 0 ) {
- height += 1;
- correction -= 1;
- }
- $( item ).css( {
- height: height,
- lineHeight: height + "px"
- } );
- } );
+ if ( this._endEffect ) {
+ setTimeout( function () {
+ self._setEndEffect( "out" );
+ self._hideScrollBars();
+ self._hideOverflowIndicator();
+ }, 300 );
}
- // position the shortcut flush with the top of the first list divider
- shortcutsTop = dividers.first().position().top;
- self.shortcutsContainer.css( 'top', shortcutsTop );
-
- // make the scrollview clip tall enough to show the whole of the shortcutslist
- minClipHeight = shortcutsTop + self.shortcutsContainer.outerHeight() + 'px';
- self.scrollview.css( 'min-height', minClipHeight );
-
- self._setTimer( false );
- self._setTimer( true );
- }
- } );
+ return !this._didDrag;
+ },
- $( document ).bind( "pagecreate create", function ( e ) {
- $( $.tizen.fastscroll.prototype.options.initSelector, e.target )
- .not( ":jqmData(role='none'), :jqmData(role='nojs')" )
- .fastscroll();
- } );
+ _setGestureScroll: function ( sx, sy ) {
+ var self = this,
+ reset = function () {
+ clearTimeout( self._gesture_timer );
+ self._gesture_dir = 0;
+ self._gesture_timer = undefined;
+ },
+ direction = {
+ top: 0,
+ bottom: 1,
+ left: 2,
+ right: 3
+ };
-} ( jQuery ) );
+ if ( !sy && !sx ) {
+ return false;
+ }
+ if ( Math.abs( sx ) > Math.abs( sy ) ) {
+ dir = sx > 0 ? direction.left : direction.right;
+ } else {
+ dir = sy > 0 ? direction.top : direction.bottom;
+ }
+ if ( !this._gesture_timer ) {
+ this._gesture_dir = dir;
-/*
- *
- * This software is licensed under the MIT licence (as defined by the OSI at
- * http://www.opensource.org/licenses/mit-license.php)
- *
- * ***************************************************************************
- * Copyright (C) 2011 by Intel Corporation Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- */
+ this._gesture_timer = setTimeout( function () {
+ reset();
+ }, 1000 );
-// Ensure that the given namespace is defined. If not, define it to be an empty object.
-// This is kinda like the mkdir -p command.
+ return false;
+ }
-var ensureNS = (function () {
- var internalCache = {};
- return function ensureNS (ns) { // name just for debugging purposes
- var nsArr = ns.split(".").reverse(),
- nsSoFar = "",
- buffer = "",
- leaf = "",
- l = nsArr.length;
- while(--l >= 0) {
- leaf = nsArr[l];
- nsSoFar = nsSoFar + (nsSoFar.length > 0 ? "." : "") + leaf;
- if (!internalCache[nsSoFar]) {
- internalCache[nsSoFar] = true;
- buffer += "!window." + nsSoFar + ' && (window.' + nsSoFar + " = {});\n";
+ if ( this._gesture_dir !== dir ) {
+ reset();
+ return false;
}
- }
- buffer.length && (new Function(buffer))();
- };
-})();
+ return false;
+ },
+ _enableTracking: function () {
+ this._dragging = true;
+ },
-/*
- * Dual licensed under the MIT (http://www.opensource.org/licenses/mit-license.php) and GPL licenses
- * http://phpjs.org/functions/range
- * original by: Waldo Malqui Silva
- * version: 1107.2516
- */
-function range( low, high, step ) {
- // Create an array containing the range of integers or characters
- // from low to high (inclusive)
- //
- // version: 1107.2516
- // discuss at: http://phpjs.org/functions/range
- // + original by: Waldo Malqui Silva
- // * example 1: range ( 0, 12 );
- // * returns 1: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]
- // * example 2: range( 0, 100, 10 );
- // * returns 2: [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100]
- // * example 3: range( 'a', 'i' );
- // * returns 3: ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i']
- // * example 4: range( 'c', 'a' );
- // * returns 4: ['c', 'b', 'a']
- var matrix = [],
- inival,
- endval,
- plus,
- walker = step || 1,
- chars = false;
+ _disableTracking: function () {
+ this._dragging = false;
+ },
- if (!isNaN(low) && !isNaN(high)) {
- inival = low;
- endval = high;
- } else if (isNaN(low) && isNaN(high)) {
- chars = true;
- inival = low.charCodeAt(0);
- endval = high.charCodeAt(0);
- } else {
- inival = (isNaN(low) ? 0 : low);
- endval = (isNaN(high) ? 0 : high);
- }
+ _showScrollBars: function ( interval ) {
+ var vclass = "ui-scrollbar-visible",
+ self = this;
- plus = ((inival > endval) ? false : true);
- if (plus) {
- while (inival <= endval) {
- matrix.push(((chars) ? String.fromCharCode(inival) : inival));
- inival += walker;
- }
- } else {
- while (inival >= endval) {
- matrix.push(((chars) ? String.fromCharCode(inival) : inival));
- inival -= walker;
- }
- }
+ if ( !this.options.showScrollBars ) {
+ return;
+ }
+ if ( this._scrollbar_showed ) {
+ return;
+ }
- return matrix;
-}
+ if ( this._$vScrollBar ) {
+ this._$vScrollBar.addClass( vclass );
+ }
+ if ( this._$hScrollBar ) {
+ this._$hScrollBar.addClass( vclass );
+ }
+ this._scrollbar_showed = true;
-\r
-/* ***************************************************************************\r
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.\r
- *\r
- * Permission is hereby granted, free of charge, to any person obtaining a\r
- * copy of this software and associated documentation files (the "Software"),\r
- * to deal in the Software without restriction, including without limitation\r
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,\r
- * and/or sell copies of the Software, and to permit persons to whom the\r
- * Software is furnished to do so, subject to the following conditions:\r
- *\r
- * The above copyright notice and this permission notice shall be included in\r
- * all copies or substantial portions of the Software.\r
- *\r
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\r
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\r
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\r
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\r
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING\r
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER\r
- * DEALINGS IN THE SOFTWARE.\r
- * ***************************************************************************\r
- *\r
- * Authors: Hyunsook Park <hyunsook.park@samsung.com>\r
- * Wonseop Kim <wonseop.kim@samsung.com>\r
-*/\r
-\r
-( function ( $, undefined ) {\r
- $.webgl = {};\r
-\r
- $.webgl.shader = {\r
- _vertexShader: null,\r
- _fragmentShader: null,\r
-\r
- deleteShaders: function ( gl ) {\r
- gl.deleteShader( this._vertexShader );\r
- gl.deleteShader( this._fragmentShader );\r
- },\r
-\r
- addShaderProgram : function ( gl, vs, fs, isFile ) {\r
- var shaderProgram,\r
- vertexShaderSource = {},\r
- fragmentShaderSource = {};\r
-\r
- if ( isFile ) {\r
- vertexShaderSource = this.loadShaderFile( vs );\r
- fragmentShaderSource = this.loadShaderFile( fs );\r
- } else {\r
- vertexShaderSource.source = vs;\r
- fragmentShaderSource.source = fs;\r
- }\r
-\r
- this._vertexShader = this.getShader( gl, gl.VERTEX_SHADER, vertexShaderSource );\r
- this._fragmentShader = this.getShader( gl, gl.FRAGMENT_SHADER, fragmentShaderSource );\r
-\r
- shaderProgram = gl.createProgram();\r
- gl.attachShader( shaderProgram, this._vertexShader);\r
- gl.attachShader( shaderProgram, this._fragmentShader);\r
- gl.linkProgram( shaderProgram );\r
-\r
- if ( !gl.getProgramParameter( shaderProgram, gl.LINK_STATUS ) ) {\r
- window.alert( "Could not initialize Shaders!" );\r
- }\r
- return shaderProgram;\r
- },\r
-\r
- loadShaderFile : function ( path ) {\r
- var cache = null;\r
- $.ajax({\r
- async : false,\r
- url : path,\r
- success : function ( result ) {\r
- cache = {\r
- source: result\r
- };\r
- }\r
- });\r
- return cache;\r
- },\r
-\r
- getShader: function ( gl, type, script ) {\r
- var shader;\r
-\r
- if ( !gl || !type || !script ) {\r
- return null;\r
- }\r
-\r
- shader = gl.createShader( type );\r
-\r
- gl.shaderSource( shader, script.source );\r
- gl.compileShader( shader );\r
-\r
- if ( !gl.getShaderParameter( shader, gl.COMPILE_STATUS ) ) {\r
- window.alert( gl.getShaderInfoLog( shader ) );\r
- gl.deleteShader( shader );\r
- return null;\r
- }\r
- return shader;\r
- }\r
- };\r
-\r
- $.webgl.buffer = {\r
- attribBufferData: function ( gl, attribArray ) {\r
- var attribBuffer = gl.createBuffer();\r
-\r
- gl.bindBuffer( gl.ARRAY_BUFFER, attribBuffer );\r
- gl.bufferData( gl.ARRAY_BUFFER, attribArray, gl.STATIC_DRAW );\r
- gl.bindBuffer( gl.ARRAY_BUFFER, null );\r
-\r
- return attribBuffer;\r
- }\r
- };\r
-\r
-} ( jQuery ) );\r
-\r
+ if ( interval ) {
+ setTimeout( function () {
+ self._hideScrollBars();
+ }, interval );
+ }
+ },
+
+ _hideScrollBars: function () {
+ var vclass = "ui-scrollbar-visible";
+
+ if ( !this.options.showScrollBars ) {
+ return;
+ }
+ if ( !this._scrollbar_showed ) {
+ return;
+ }
+
+ if ( this._$vScrollBar ) {
+ this._$vScrollBar.removeClass( vclass );
+ }
+ if ( this._$hScrollBar ) {
+ this._$hScrollBar.removeClass( vclass );
+ }
+
+ this._scrollbar_showed = false;
+ },
+
+ _setOverflowIndicator: function ( dir ) {
+ if ( dir === 1 ) {
+ this._opacity_top = "0";
+ this._opacity_bottom = "0.8";
+ } else if ( dir === 0 ) {
+ this._opacity_top = "0.8";
+ this._opacity_bottom = "0";
+ } else {
+ this._opacity_top = "0.5";
+ this._opacity_bottom = "0.5";
+ }
+ },
+
+ _showOverflowIndicator: function () {
+ if ( !this.options.overflowEnable || !this._overflowAvail || this._softkeyboard ) {
+ return;
+ }
+ this._overflow_top.animate( { opacity: this._opacity_top }, 300 );
+ this._overflow_bottom.animate( { opacity: this._opacity_bottom }, 300 );
-/* ***************************************************************************
- Flora License
+ this._overflow_showed = true;
+ },
- Version 1.0, April, 2013
+ _hideOverflowIndicator: function () {
+ if ( !this.options.overflowEnable || !this._overflowAvail || this._softkeyboard ) {
+ return;
+ }
- http://floralicense.org/license/
+ if ( this._overflow_showed === false ) {
+ return;
+ }
- TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+ this._overflow_top.animate( { opacity: 0 }, 300 );
+ this._overflow_bottom.animate( { opacity: 0 }, 300 );
- 1. Definitions.
+ this._overflow_showed = false;
+ this._setOverflowIndicator();
+ },
- "License" shall mean the terms and conditions for use, reproduction,
- and distribution as defined by Sections 1 through 9 of this document.
+ _add_event: function () {
+ var self = this,
+ $c = this._$clip,
+ $v = this._$view;
- "Licensor" shall mean the copyright owner or entity authorized by
- the copyright owner that is granting the License.
+ if ( this.options.eventType === "mouse" ) {
+ this._dragEvt = "mousedown mousemove mouseup click mousewheel";
- "Legal Entity" shall mean the union of the acting entity and
- all other entities that control, are controlled by, or are
- under common control with that entity. For the purposes of
- this definition, "control" means (i) the power, direct or indirect,
- to cause the direction or management of such entity,
- whether by contract or otherwise, or (ii) ownership of fifty percent (50%)
- or more of the outstanding shares, or (iii) beneficial ownership of
- such entity.
+ this._dragCB = function ( e ) {
+ switch ( e.type ) {
+ case "mousedown":
+ return self._handleDragStart( e,
+ e.clientX, e.clientY );
- "You" (or "Your") shall mean an individual or Legal Entity
- exercising permissions granted by this License.
+ case "mousemove":
+ return self._handleDragMove( e,
+ e.clientX, e.clientY );
- "Source" form shall mean the preferred form for making modifications,
- including but not limited to software source code, documentation source,
- and configuration files.
+ case "mouseup":
+ return self._handleDragStop( e );
- "Object" form shall mean any form resulting from mechanical
- transformation or translation of a Source form, including but
- not limited to compiled object code, generated documentation,
- and conversions to other media types.
+ case "click":
+ return !self._didDrag;
- "Work" shall mean the work of authorship, whether in Source or Object form,
- made available under the License, as indicated by a copyright notice
- that is included in or attached to the work (an example is provided
- in the Appendix below).
+ case "mousewheel":
+ var old = self.getScrollPosition();
+ self.scrollTo( -old.x,
+ -(old.y - e.originalEvent.wheelDelta) );
+ break;
+ }
+ };
+ } else {
+ this._dragEvt = "touchstart touchmove touchend click";
- "Derivative Works" shall mean any work, whether in Source or Object form,
- that is based on (or derived from) the Work and for which the editorial
- revisions, annotations, elaborations, or other modifications represent,
- as a whole, an original work of authorship. For the purposes of this License,
- Derivative Works shall not include works that remain separable from,
- or merely link (or bind by name) to the interfaces of, the Work and
- Derivative Works thereof.
+ this._dragCB = function ( e ) {
+ var touches = e.originalEvent.touches;
- "Contribution" shall mean any work of authorship, including the original
- version of the Work and any modifications or additions to that Work or
- Derivative Works thereof, that is intentionally submitted to Licensor
- for inclusion in the Work by the copyright owner or by an individual or
- Legal Entity authorized to submit on behalf of the copyright owner.
- For the purposes of this definition, "submitted" means any form of
- electronic, verbal, or written communication sent to the Licensor or
- its representatives, including but not limited to communication on
- electronic mailing lists, source code control systems, and issue
- tracking systems that are managed by, or on behalf of, the Licensor
- for the purpose of discussing and improving the Work, but excluding
- communication that is conspicuously marked or otherwise designated
- in writing by the copyright owner as "Not a Contribution."
+ switch ( e.type ) {
+ case "touchstart":
+ if ( touches.length != 1) {
+ return;
+ }
- "Contributor" shall mean Licensor and any individual or Legal Entity
- on behalf of whom a Contribution has been received by Licensor and
- subsequently incorporated within the Work.
+ return self._handleDragStart( e,
+ touches[0].pageX, touches[0].pageY );
- "Tizen Certified Platform" shall mean a software platform that complies
- with the standards set forth in the Tizen Compliance Specification
- and passes the Tizen Compliance Tests as defined from time to time
- by the Tizen Technical Steering Group and certified by the Tizen
- Association or its designated agent.
+ case "touchmove":
+ if ( touches.length != 1) {
+ return;
+ }
- 2. Grant of Copyright License. Subject to the terms and conditions of
- this License, each Contributor hereby grants to You a perpetual,
- worldwide, non-exclusive, no-charge, royalty-free, irrevocable
- copyright license to reproduce, prepare Derivative Works of,
- publicly display, publicly perform, sublicense, and distribute the
- Work and such Derivative Works in Source or Object form.
+ return self._handleDragMove( e,
+ touches[0].pageX, touches[0].pageY );
- 3. Grant of Patent License. Subject to the terms and conditions of
- this License, each Contributor hereby grants to You a perpetual,
- worldwide, non-exclusive, no-charge, royalty-free, irrevocable
- (except as stated in this section) patent license to make, have made,
- use, offer to sell, sell, import, and otherwise transfer the Work
- solely as incorporated into a Tizen Certified Platform, where such
- license applies only to those patent claims licensable by such
- Contributor that are necessarily infringed by their Contribution(s)
- alone or by combination of their Contribution(s) with the Work solely
- as incorporated into a Tizen Certified Platform to which such
- Contribution(s) was submitted. If You institute patent litigation
- against any entity (including a cross-claim or counterclaim
- in a lawsuit) alleging that the Work or a Contribution incorporated
- within the Work constitutes direct or contributory patent infringement,
- then any patent licenses granted to You under this License for that
- Work shall terminate as of the date such litigation is filed.
+ case "touchend":
+ if ( touches.length != 0) {
+ return;
+ }
- 4. Redistribution. You may reproduce and distribute copies of the
- Work or Derivative Works thereof pursuant to the copyright license
- above, in any medium, with or without modifications, and in Source or
- Object form, provided that You meet the following conditions:
+ return self._handleDragStop( e );
- 1. You must give any other recipients of the Work or Derivative Works
- a copy of this License; and
- 2. You must cause any modified files to carry prominent notices stating
- that You changed the files; and
- 3. You must retain, in the Source form of any Derivative Works that
- You distribute, all copyright, patent, trademark, and attribution
- notices from the Source form of the Work, excluding those notices
- that do not pertain to any part of the Derivative Works; and
- 4. If the Work includes a "NOTICE" text file as part of its distribution,
- then any Derivative Works that You distribute must include a readable
- copy of the attribution notices contained within such NOTICE file,
- excluding those notices that do not pertain to any part of
- the Derivative Works, in at least one of the following places:
- within a NOTICE text file distributed as part of the Derivative Works;
- within the Source form or documentation, if provided along with the
- Derivative Works; or, within a display generated by the Derivative Works,
- if and wherever such third-party notices normally appear.
- The contents of the NOTICE file are for informational purposes only
- and do not modify the License.
+ case "click":
+ return !self._didDrag;
+ }
+ };
+ }
- You may add Your own attribution notices within Derivative Works
- that You distribute, alongside or as an addendum to the NOTICE text
- from the Work, provided that such additional attribution notices
- cannot be construed as modifying the License. You may add Your own
- copyright statement to Your modifications and may provide additional or
- different license terms and conditions for use, reproduction, or
- distribution of Your modifications, or for any such Derivative Works
- as a whole, provided Your use, reproduction, and distribution of
- the Work otherwise complies with the conditions stated in this License.
+ $v.bind( this._dragEvt, this._dragCB );
- 5. Submission of Contributions. Unless You explicitly state otherwise,
- any Contribution intentionally submitted for inclusion in the Work
- by You to the Licensor shall be under the terms and conditions of
- this License, without any additional terms or conditions.
- Notwithstanding the above, nothing herein shall supersede or modify
- the terms of any separate license agreement you may have executed
- with Licensor regarding such Contributions.
+ $v.bind( "keydown", function ( e ) {
+ var elem,
+ elem_top,
+ scroll_top = $( window ).scrollTop() - window.screenTop,
+ screen_h;
- 6. Trademarks. This License does not grant permission to use the trade
- names, trademarks, service marks, or product names of the Licensor,
- except as required for reasonable and customary use in describing the
- origin of the Work and reproducing the content of the NOTICE file.
+ if ( e.keyCode == 9 ) {
+ return false;
+ }
- 7. Disclaimer of Warranty. Unless required by applicable law or
- agreed to in writing, Licensor provides the Work (and each
- Contributor provides its Contributions) on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
- implied, including, without limitation, any warranties or conditions
- of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
- PARTICULAR PURPOSE. You are solely responsible for determining the
- appropriateness of using or redistributing the Work and assume any
- risks associated with Your exercise of permissions under this License.
+ elem = $c.find(".ui-focus");
- 8. Limitation of Liability. In no event and under no legal theory,
- whether in tort (including negligence), contract, or otherwise,
- unless required by applicable law (such as deliberate and grossly
- negligent acts) or agreed to in writing, shall any Contributor be
- liable to You for damages, including any direct, indirect, special,
- incidental, or consequential damages of any character arising as a
- result of this License or out of the use or inability to use the
- Work (including but not limited to damages for loss of goodwill,
- work stoppage, computer failure or malfunction, or any and all
- other commercial damages or losses), even if such Contributor
- has been advised of the possibility of such damages.
+ if ( elem === undefined ) {
+ return;
+ }
+
+ elem_top = elem.offset().top - scroll_top;
+ screen_h = $c.offset().top + $c.height() - elem.height();
+
+ if ( self._softkeyboard ) {
+ screen_h -= self._softkeyboardHeight;
+ }
+
+ if ( ( elem_top < $c.offset().top ) || ( elem_top > screen_h ) ) {
+ self.scrollTo( 0, self._sy -
+ ( elem_top - $c.offset().top - elem.height() ) );
+ }
+
+ return;
+ });
+
+ $v.bind( "keyup", function ( e ) {
+ var input,
+ elem,
+ elem_top,
+ scroll_top = $( window ).scrollTop() - window.screenTop,
+ screen_h;
+
+ if ( e.keyCode != 9 ) {
+ return;
+ }
+
+ /* Tab Key */
- 9. Accepting Warranty or Additional Liability. While redistributing
- the Work or Derivative Works thereof, You may choose to offer,
- and charge a fee for, acceptance of support, warranty, indemnity,
- or other liability obligations and/or rights consistent with this
- License. However, in accepting such obligations, You may act only
- on Your own behalf and on Your sole responsibility, not on behalf
- of any other Contributor, and only if You agree to indemnify,
- defend, and hold each Contributor harmless for any liability
- incurred by, or claims asserted against, such Contributor by reason
- of your accepting any such warranty or additional liability.
+ input = $( this ).find(":input");
- END OF TERMS AND CONDITIONS
+ for ( i = 0; i < input.length; i++ ) {
+ if ( !$( input[i] ).hasClass("ui-focus") ) {
+ continue;
+ }
- APPENDIX: How to apply the Flora License to your work
+ if ( i + 1 == input.length ) {
+ elem = $( input[0] );
+ } else {
+ elem = $( input[i + 1] );
+ }
- To apply the Flora License to your work, attach the following
- boilerplate notice, with the fields enclosed by brackets "[]"
- replaced with your own identifying information. (Don't include
- the brackets!) The text should be enclosed in the appropriate
- comment syntax for the file format. We also recommend that a
- file or class name and description of purpose be included on the
- same "printed page" as the copyright notice for easier
- identification within third-party archives.
+ elem_top = elem.offset().top - scroll_top;
+ screen_h = $c.offset().top + $c.height() - elem.height();
- Copyright [yyyy] [name of copyright owner]
+ if ( self._softkeyboard ) {
+ screen_h -= self._softkeyboardHeight;
+ }
- Licensed under the Flora License, Version 1.0 (the "License");
- you may not use this file except in compliance with the License.
- You may obtain a copy of the License at
+ if ( ( elem_top < 0 ) || ( elem_top > screen_h ) ) {
+ self.scrollTo( 0, self._sy - elem_top +
+ elem.height() + $c.offset().top, 0);
+ }
- http://floralicense.org/license/
+ elem.focus();
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- See the License for the specific language governing permissions and
- limitations under the License.
+ break;
+ }
- * Author: Minkyu Kang <mk7.kang@samsung.com>
- */
+ return false;
+ });
-/*
- * Pinch Event
- *
- * Events
- * pinchstart: triggered when start the touched two points
- * pinch: triggered when move the touch point after pinchstart event occured
- * pinchend: triggered when touchend event after pinchstart event occured
- *
- * Parameters
- * point: touched points
- * ratio: origin point-to-current point ratio for moving distance
- *
- * $("#pinch").bind("pinch", function (e, p) {
- * console.log("point[0].x: " + p.point[0].x);
- * console.log("point[0].y: " + p.point[0].y);
- * console.log("point[1].x: " + p.point[1].x);
- * console.log("point[1].y: " + p.point[1].y);
- * console.log("ratio: " + p.ratio);
- * });
- *
- * Options
- * $.mobile.pinch.enabled: true or false
- * $.mobile.pinch.min: minimum value of ratio
- * $.mobile.pinch.max: maximum value of ratio
- * $.mobile.pinch.factor: scale factor of ratio
- * $.mobile.pinch.threshold: move threshold of ratio
- * $.mobile.pinch.interval: interval for pinch event
- */
+ $c.bind( "updatelayout", function ( e ) {
+ var sy,
+ vh,
+ view_h = self._getViewHeight();
+ if ( !$c.height() || !view_h ) {
+ self.scrollTo( 0, 0, 0 );
+ return;
+ }
-( function( $, window, undefined ) {
+ sy = $c.height() - view_h;
+ vh = view_h - self._view_height;
-pinch_event = {
- setup: function () {
- var thisObject = this,
- $this = $( thisObject );
+ self._view_height = view_h;
- if ( !$.mobile.support.touch ) {
- return;
- }
+ if ( vh == 0 || vh > $c.height() / 2 ) {
+ return;
+ }
- function getSize( point ) {
- var x = point[0].x - point[1].x,
- y = point[0].y - point[1].y;
+ if ( sy > 0 ) {
+ self.scrollTo( 0, 0, 0 );
+ } else if ( self._sy - sy <= -vh ) {
+ self.scrollTo( 0, self._sy,
+ self.options.snapbackDuration );
+ } else if ( self._sy - sy <= vh + self.options.moveThreshold ) {
+ self.scrollTo( 0, sy,
+ self.options.snapbackDuration );
+ }
+ });
- return Math.abs( x * y );
- }
+ $( window ).bind( "resize", function ( e ) {
+ var focused,
+ view_h = self._getViewHeight();
- function getParameter( point, ratio ) {
- return { point: point, ratio: ratio };
- }
+ if ( $(".ui-page-active").get(0) !== $c.closest(".ui-page").get(0) ) {
+ return;
+ }
- $this.bind( "touchstart", function ( event ) {
- var data = event.originalEvent.touches,
- origin,
- last_ratio = 1,
- processing = false;
+ if ( !$c.height() || !view_h ) {
+ return;
+ }
- if ( !$.mobile.pinch.enabled ) {
- return;
- }
+ focused = $c.find(".ui-focus");
- if ( data.length != 2 ) {
- return;
- }
+ if ( focused ) {
+ focused.trigger("resize.scrollview");
+ }
- origin = [
- { x: data[0].pageX, y: data[0].pageY },
- { x: data[1].pageX, y: data[1].pageY }
- ];
+ /* calibration - after triggered throttledresize */
+ setTimeout( function () {
+ if ( self._sy < $c.height() - self._getViewHeight() ) {
+ self.scrollTo( 0, $c.height() - self._getViewHeight(),
+ self.options.overshootDuration );
+ }
+ }, 260 );
- $( event.target ).trigger( "pinchstart", getParameter( origin, undefined ) );
+ self._view_height = view_h;
+ });
- function pinchHandler( event ) {
- var data = event.originalEvent.touches,
- current,
- ratio,
- delta,
- factor = $( window ).width() / $.mobile.pinch.factor;
+ $( window ).bind( "vmouseout", function ( e ) {
+ var drag_stop = false;
- if ( processing ) {
+ if ( $(".ui-page-active").get(0) !== $c.closest(".ui-page").get(0) ) {
return;
}
- if ( !origin ) {
+ if ( !self._dragging ) {
return;
}
- current = [
- { x: data[0].pageX, y: data[0].pageY },
- { x: data[1].pageX, y: data[1].pageY }
- ];
+ if ( e.pageX < 0 || e.pageX > $( window ).width() ) {
+ drag_stop = true;
+ }
- delta = Math.sqrt( getSize( current ) / getSize( origin ) ) ;
- if( delta ) {
- ratio = delta;
+ if ( e.pageY < 0 || e.pageY > $( window ).height() ) {
+ drag_stop = true;
}
- if ( ratio < $.mobile.pinch.min ) {
- ratio = $.mobile.pinch.min;
- } else if ( ratio > $.mobile.pinch.max ) {
- ratio = $.mobile.pinch.max;
+ if ( drag_stop ) {
+ self._hideScrollBars();
+ self._hideOverflowIndicator();
+ self._disableTracking();
}
+ });
- if ( Math.abs( ratio - last_ratio ) < $.mobile.pinch.threshold ) {
+ this._softkeyboard = false;
+ this._softkeyboardHeight = 0;
+
+ window.addEventListener( "softkeyboardchange", function ( e ) {
+ if ( $(".ui-page-active").get(0) !== $c.closest(".ui-page").get(0) ) {
return;
}
- $( event.target ).trigger( "pinch", getParameter( current, ratio ) );
+ self._softkeyboard = ( e.state === "on" ? true : false );
+ self._softkeyboardHeight = parseInt( e.height ) *
+ ( $( window ).width() / window.screen.availWidth );
+ });
+
+ $c.closest(".ui-page")
+ .bind( "pageshow", function ( e ) {
+ /* should be called after pagelayout */
+ setTimeout( function () {
+ self._view_height = self._getViewHeight();
+ self._set_scrollbar_size();
+ self._setScrollPosition( self._sx, self._sy );
+ self._showScrollBars( 2000 );
+ }, 0 );
+ });
+ },
+
+ _add_scrollbar: function () {
+ var $c = this._$clip,
+ prefix = "<div class=\"ui-scrollbar ui-scrollbar-",
+ suffix = "\"><div class=\"ui-scrollbar-track\"><div class=\"ui-scrollbar-thumb\"></div></div></div>";
+
+ if ( !this.options.showScrollBars ) {
+ return;
+ }
+
+ if ( this._vTracker ) {
+ $c.append( prefix + "y" + suffix );
+ this._$vScrollBar = $c.children(".ui-scrollbar-y");
+ }
+ if ( this._hTracker ) {
+ $c.append( prefix + "x" + suffix );
+ this._$hScrollBar = $c.children(".ui-scrollbar-x");
+ }
+
+ this._scrollbar_showed = false;
+ },
+
+ _add_scroll_jump: function () {
+ var $c = this._$clip,
+ self = this,
+ top_btn,
+ left_btn;
+
+ if ( !this.options.scrollJump ) {
+ return;
+ }
+
+ if ( this._vTracker ) {
+ top_btn = $( '<div class="ui-scroll-jump-top-bg">' +
+ '<div data-role="button" data-inline="true" data-icon="scrolltop" data-style="box"></div></div>' );
+ $c.append( top_btn ).trigger("create");
+
+ top_btn.bind( "vclick", function () {
+ self.scrollTo( 0, 0, self.options.overshootDuration );
+ } );
+ }
- last_ratio = ratio;
+ if ( this._hTracker ) {
+ left_btn = $( '<div class="ui-scroll-jump-left-bg">' +
+ '<div data-role="button" data-inline="true" data-icon="scrollleft" data-style="box"></div></div>' );
+ $c.append( left_btn ).trigger("create");
- if ( $.mobile.pinch.interval ) {
- processing = true;
+ left_btn.bind( "vclick", function () {
+ self.scrollTo( 0, 0, self.options.overshootDuration );
+ } );
+ }
+ },
- setTimeout( function () {
- processing = false;
- }, $.mobile.pinch.interval );
- }
+ _add_overflow_indicator: function () {
+ if ( !this.options.overflowEnable ) {
+ return;
}
- $this.bind( "touchmove", pinchHandler )
- .one( "touchend", function ( event ) {
- $this.unbind( "touchmove", pinchHandler );
- $( event.target ).trigger( "pinchend",
- getParameter( undefined, last_ratio ) );
+ this._overflow_top = $( '<div class="ui-overflow-indicator-top"></div>' );
+ this._overflow_bottom = $( '<div class="ui-overflow-indicator-bottom"></div>' );
- origin = undefined;
- current = undefined;
- last_ratio = 1;
- processing = false;
- });
- });
- }
-};
+ this._$clip.append( this._overflow_top );
+ this._$clip.append( this._overflow_bottom );
-$.event.special["pinch"] = pinch_event;
+ this._opacity_top = "0.5";
+ this._opacity_bottom = "0.5";
+ this._overflow_showed = false;
+ },
-$.mobile.pinch = {
- enabled: true,
- min: 0.1,
- max: 3,
- factor: 4,
- threshold: 0.01,
- interval: 50
-};
+ _set_scrollbar_size: function () {
+ var $c = this._$clip,
+ $v = this._$view,
+ cw = 0,
+ vw = 0,
+ ch = 0,
+ vh = 0,
+ thumb;
-})( jQuery, this );
+ if ( !this.options.showScrollBars ) {
+ return;
+ }
+ if ( this._hTracker ) {
+ cw = $c.width();
+ vw = $v.width();
+ this._maxX = cw - vw;
-\r
-/* ***************************************************************************\r
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.\r
- *\r
- * Permission is hereby granted, free of charge, to any person obtaining a\r
- * copy of this software and associated documentation files (the "Software"),\r
- * to deal in the Software without restriction, including without limitation\r
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,\r
- * and/or sell copies of the Software, and to permit persons to whom the\r
- * Software is furnished to do so, subject to the following conditions:\r
- *\r
- * The above copyright notice and this permission notice shall be included in\r
- * all copies or substantial portions of the Software.\r
- *\r
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\r
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\r
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\r
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\r
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING\r
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER\r
- * DEALINGS IN THE SOFTWARE.\r
- * ***************************************************************************\r
- *\r
- * Authors: Hyunsook Park <hyunsook.park@samsung.com>\r
- * Wonseop Kim <wonseop.kim@samsung.com>\r
-*/\r
-\r
-( function ( $, window, document, undefined ) {\r
- var _canvas, _context;\r
-\r
- function initCanvas() {\r
- if (_context) {\r
- return;\r
- }\r
- _canvas = document.createElement( 'canvas' );\r
- _context = _canvas.getContext( '2d' );\r
- }\r
-\r
- function fileSystemErrorMessage( e ) {\r
- var FileError = window.FileError,\r
- msg = '';\r
- switch ( e.code ) {\r
- case FileError.QUOTA_EXCEEDED_ERR:\r
- msg = 'QUOTA_EXCEEDED_ERR';\r
- break;\r
- case FileError.NOT_FOUND_ERR:\r
- msg = 'NOT_FOUND_ERR';\r
- break;\r
- case FileError.SECURITY_ERR:\r
- msg = 'SECURITY_ERR';\r
- break;\r
- case FileError.INVALID_MODIFICATION_ERR:\r
- msg = 'INVALID_MODIFICATION_ERR';\r
- break;\r
- case FileError.INVALID_STATE_ERR:\r
- msg = 'INVALID_STATE_ERR';\r
- break;\r
- default:\r
- msg = 'Unknown Error';\r
- break;\r
- }\r
- return msg;\r
- }\r
-\r
- function getInternalURLFromURL( url ) {\r
- var internalURL = url.replace( /\//gi, "_" );\r
- return internalURL;\r
- }\r
-\r
- function resize( imagewidth, imageheight, thumbwidth, thumbheight, fit ) {\r
- var w = 0, h = 0, x = 0, y = 0,\r
- widthratio = imagewidth / thumbwidth,\r
- heightratio = imageheight / thumbheight,\r
- maxratio = Math.max( widthratio, heightratio );\r
-\r
- if ( fit ) {\r
- w = thumbwidth;\r
- h = thumbheight;\r
- } else {\r
- if ( maxratio > 1 ) {\r
- w = imagewidth / maxratio;\r
- h = imageheight / maxratio;\r
- } else {\r
- w = imagewidth;\r
- h = imageheight;\r
- }\r
- x = ( thumbwidth - w ) / 2;\r
- y = ( thumbheight - h ) / 2;\r
- }\r
-\r
- return { w: w, h: h, x: x, y: y };\r
- }\r
-\r
- function getThumbnail( img, thumbwidth, thumbheight, fit ) {\r
- var dimensions, url;\r
- initCanvas();\r
- _canvas.width = thumbwidth;\r
- _canvas.height = thumbheight;\r
- dimensions = resize( img.width, img.height, thumbwidth, thumbheight, fit );\r
- _context.fillStyle = "#000000";\r
- _context.fillRect ( 0, 0, thumbwidth, thumbheight );\r
- _context.drawImage( img, dimensions.x, dimensions.y, dimensions.w, dimensions.h );\r
- url = _canvas.toDataURL();\r
- return url;\r
- }\r
-\r
- $.imageloader = {\r
- _grantedBytes: 1024 * 1024,\r
- getThumbnail: function ( url, _callback ) {\r
- var internalURL, canvasDataURI;\r
- function errorHandler( e ) {\r
- var msg = fileSystemErrorMessage( e );\r
- if ( _callback ) {\r
- _callback( ( msg === "NOT_FOUND_ERR" ) ? msg : null );\r
- }\r
- }\r
-\r
- internalURL = getInternalURLFromURL( url );\r
- try {\r
- canvasDataURI = localStorage.getItem( internalURL );\r
- if ( _callback ) {\r
- _callback( ( canvasDataURI === null ) ? "NOT_FOUND_ERR" : canvasDataURI );\r
- }\r
- } catch ( e ) {\r
- if ( _callback ) {\r
- _callback( ( e.type === "non_object_property_load" ) ? "NOT_FOUND_ERR" : null );\r
- }\r
- }\r
- },\r
-\r
- setThumbnail: function ( url, _callback, thumbWidth, thumbHeight, fit ) {\r
- var image, internalURL, canvasDataURI;\r
- function errorHandler( e ) {\r
- var msg = fileSystemErrorMessage( e );\r
- if ( _callback ) {\r
- _callback( ( msg === "NOT_FOUND_ERR" ) ? msg : null );\r
- }\r
- }\r
-\r
- thumbWidth = thumbWidth || 128;\r
- thumbHeight = thumbHeight || 128;\r
- fit = fit || true;\r
- image = new Image();\r
- image.onload = function () {\r
- internalURL = getInternalURLFromURL( url );\r
- canvasDataURI = getThumbnail( this, thumbWidth, thumbHeight, fit );\r
- try {\r
- localStorage.setItem( internalURL, canvasDataURI );\r
- if ( _callback ) {\r
- _callback( canvasDataURI );\r
- }\r
- } catch ( e ) {\r
- if ( _callback ) {\r
- _callback( ( e.type === "non_object_property_load" ) ? "NOT_FOUND_ERR" : null );\r
- }\r
- }\r
- };\r
- image.src = url;\r
- },\r
-\r
- removeThumbnail: function ( url ) {\r
- var internalURL;\r
- function errorHandler( e ) {\r
- fileSystemErrorMessage( e );\r
- }\r
-\r
- internalURL = getInternalURLFromURL( url );\r
- try {\r
- localStorage.removeItem( internalURL );\r
- } catch ( e ) {\r
- throw e;\r
- }\r
- }\r
- };\r
-\r
-} ( jQuery, window, document ) );\r
-\r
+ if ( this._maxX > 0 ) {
+ this._maxX = 0;
+ }
+ if ( this._$hScrollBar && vw ) {
+ thumb = this._$hScrollBar.find(".ui-scrollbar-thumb");
+ thumb.css( "width", (cw >= vw ? "0" :
+ (Math.floor(cw / vw * 100) || 1) + "%") );
+ }
+ }
+
+ if ( this._vTracker ) {
+ ch = $c.height();
+ vh = this._getViewHeight();
+ this._maxY = ch - vh;
+ if ( this._maxY > 0 || vh === 0 ) {
+ this._maxY = 0;
+ }
+ if ( ( this._$vScrollBar && vh ) || vh === 0 ) {
+ thumb = this._$vScrollBar.find(".ui-scrollbar-thumb");
+ thumb.css( "height", (ch >= vh ? "0" :
+ (Math.floor(ch / vh * 100) || 1) + "%") );
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Author: Sanghee Lee <sang-hee.lee@samsung.com>
-*/
+ this._overflowAvail = !!thumb.height();
+ }
+ }
+ }
+ });
-/**
- * Splitview is a widget which can show different HTML contents at the same time on each divided pane.
- * A user can place Splitview controls on JQuery Mobile's Content area and arrange two panes on the widget.
- * And HTML fragments or another Splitview also can be placed on the pane.
- * The number of panes inside of Splitview is restricted as two.
- * If a user define only one pane in Splitview, a empty pane will be added automatically,
- * on the other hand, if 3 or more panes are defined in Splitview, the panes after two will be ignored and removed from the DOM tree.
- * The HTML fragments of a pane should be composed of elements describing a part of Web page (e.g. <div>...</div>).
- * Also widgets can be included in the HTML fragments.
- *
- * HTML Attributes:
- *
- * data-fixed : The resizing mode of panes - fixed and flexible mode.
- * If the value is true, the panes' sizes will be fixed, or if not, it will be flexible. (Default : false)
- * data-divider-vertical : The direction of dividers.
- * If the value is true, the panes will be placed in horizontal direction,
- * or if not, it will be placed in vertical direction. (Default : "true")
- * data-ratio : The ratio of two panes' widths or heights. (Default : [ 1/2, 1/2 ]
- *
- * APIs:
- *
- * pane ( id [ , element ] )
- * : This method replaces child contents of a pane indicated by id attribute with contents of inputted element.
- * If second argument is not specified, it will act as a getter method.
- * The string of id has to be started with "#" which means "id" of CSS selectors.
- * maximize ( id )
- * : This method maximizes a pane's size indicated by id.
- * The string of id has to be started with "#" which means "id" of CSS selectors.
- * restore ()
- * : This method restores all panes' sizes to the ratio prior to maximization.
- *
- * Examples:
- *
- * <div data-role="splitview" data-fixed="false" data-divider-vertical="true" data-ratio="0.5, 0.5">
- * <div class="ui-pane">pane0</div>
- * <div class="ui-pane">pane1</div>
- * </div>
- *
- */
+ $.extend( MomentumTracker.prototype, {
+ start: function ( pos, speed, duration, minPos, maxPos ) {
+ var tstate = ( pos < minPos || pos > maxPos ) ?
+ tstates.snapback : tstates.scrolling,
+ pos_temp;
+ this.state = ( speed !== 0 ) ? tstate : tstates.done;
+ this.pos = pos;
+ this.speed = speed;
+ this.duration = ( this.state === tstates.snapback ) ?
+ this.options.snapbackDuration : duration;
+ this.minPos = minPos;
+ this.maxPos = maxPos;
-/**
- @class Splitview
- Splitview widget enables a user to place and arrange several panes. Each divided pane can show repective HTML contents.
+ this.fromPos = ( this.state === tstates.snapback ) ? this.pos : 0;
+ pos_temp = ( this.pos < this.minPos ) ? this.minPos : this.maxPos;
+ this.toPos = ( this.state === tstates.snapback ) ? pos_temp : 0;
- To add a Splitview widget to the application, use the following code:
+ this.startTime = getCurrentTime();
+ },
- <div data-role="splitview" data-fixed="false" data-divider-vertical="true" data-ratio="0.5, 0.5">
- <div class="ui-pane">pane0</div>
- <div class="ui-pane">pane1</div>
- </div>
-*/
+ reset: function () {
+ this.state = tstates.done;
+ this.pos = 0;
+ this.speed = 0;
+ this.minPos = 0;
+ this.maxPos = 0;
+ this.duration = 0;
+ this.remained = 0;
+ },
-/**
- @property {Boolean} data-fixed
- The resizing mode of panes - fixed and flexible mode.
-*/
+ update: function ( overshootEnable ) {
+ var state = this.state,
+ cur_time = getCurrentTime(),
+ duration = this.duration,
+ elapsed = cur_time - this.startTime,
+ dx,
+ x,
+ didOverShoot;
-/**
- @property {Boolean} data-divider-vertical
- The direction of dividers - horizontal or vertical.
- */
+ if ( state === tstates.done ) {
+ return this.pos;
+ }
-/**
- @property {Array} data-ratio
- The ratio of two panes' widths or heights.
-*/
+ elapsed = elapsed > duration ? duration : elapsed;
-/**
- @method pane
- This method replaces child contents of a pane indicated by id attribute with contents of inputted element.
- If second argument is not specified, it will act as a getter method.
+ this.remained = duration - elapsed;
- <div data-role="splitview">
- <div class="ui-pane" id="pane0">pane0</div>
- <div class="ui-pane" id="pane1">pane1</div>
- </div>
- $(".selector").splitview("pane", id, element);
-*/
+ if ( state === tstates.scrolling || state === tstates.overshot ) {
+ dx = this.speed *
+ ( 1 - $.easing[this.easing]( elapsed / duration,
+ elapsed, 0, 1, duration ) );
-/**
- @method maximize
- This method maximizes a pane's size indicated by id.
+ x = this.pos + dx;
+
+ didOverShoot = ( state === tstates.scrolling ) &&
+ ( x < this.minPos || x > this.maxPos );
+
+ if ( didOverShoot ) {
+ x = ( x < this.minPos ) ? this.minPos : this.maxPos;
+ }
+
+ this.pos = x;
+
+ if ( state === tstates.overshot ) {
+ if ( !overshootEnable ) {
+ this.state = tstates.done;
+ }
+ if ( elapsed >= duration ) {
+ this.state = tstates.snapback;
+ this.fromPos = this.pos;
+ this.toPos = ( x < this.minPos ) ?
+ this.minPos : this.maxPos;
+ this.duration = this.options.snapbackDuration;
+ this.startTime = cur_time;
+ elapsed = 0;
+ }
+ } else if ( state === tstates.scrolling ) {
+ if ( didOverShoot && overshootEnable ) {
+ this.state = tstates.overshot;
+ this.speed = dx / 2;
+ this.duration = this.options.overshootDuration;
+ this.startTime = cur_time;
+ } else if ( elapsed >= duration ) {
+ this.state = tstates.done;
+ }
+ }
+ } else if ( state === tstates.snapback ) {
+ if ( elapsed >= duration ) {
+ this.pos = this.toPos;
+ this.state = tstates.done;
+ } else {
+ this.pos = this.fromPos + (( this.toPos - this.fromPos ) *
+ $.easing[this.easing]( elapsed / duration,
+ elapsed, 0, 1, duration ));
+ }
+ }
+
+ return this.pos;
+ },
+
+ done: function () {
+ return this.state === tstates.done;
+ },
+
+ isMin: function () {
+ return this.pos === this.minPos;
+ },
+
+ isMax: function () {
+ return this.pos === this.maxPos;
+ },
+
+ isAvail: function () {
+ return !( this.minPos === this.maxPos );
+ },
+
+ getRemained: function () {
+ return this.remained;
+ },
+
+ getPosition: function () {
+ return this.pos;
+ }
+ });
+
+ $( document ).bind( 'pagecreate create', function ( e ) {
+ var $page = $( e.target ),
+ content_scroll = $page.find(".ui-content").jqmData("scroll");
+
+ /* content scroll */
+ if ( $.support.scrollview === undefined ) {
+ $.support.scrollview = true;
+ }
+
+ if ( $.support.scrollview === true && content_scroll === undefined ) {
+ content_scroll = "y";
+ }
+
+ if ( content_scroll !== "y" ) {
+ content_scroll = "none";
+ }
+
+ $page.find(".ui-content").attr( "data-scroll", content_scroll );
+
+ $page.find(":jqmData(scroll)").not(".ui-scrollview-clip").each( function () {
+ if ( $( this ).hasClass("ui-scrolllistview") ) {
+ $( this ).scrolllistview();
+ } else {
+ var st = $( this ).jqmData("scroll"),
+ dir = st && ( st.search(/^[xy]/) !== -1 ) ? st : null,
+ content = $(this).hasClass("ui-content"),
+ opts;
+
+ if ( st === "none" ) {
+ return;
+ }
- <div data-role="splitview">
- <div class="ui-pane" id="pane0">pane0</div>
- <div class="ui-pane" id="pane1">pane1</div>
- </div>
- $(".selector").splitview("maximize", id);
-*/
+ opts = {
+ direction: dir || undefined,
+ overflowEnable: content,
+ scrollMethod: $( this ).jqmData("scroll-method") || undefined,
+ scrollJump: $( this ).jqmData("scroll-jump") || undefined
+ };
-/**
- @method restore
- This method restores all panes' sizes to the ratio prior to maximization.
+ $( this ).scrollview( opts );
+ }
+ });
+ });
- <div data-role="splitview">
- <div class="ui-pane" id="pane0">pane0</div>
- <div class="ui-pane" id="pane1">pane1</div>
- </div>
- $(".selector").splitview("restore");
-*/
+ $( document ).bind( 'pageshow', function ( e ) {
+ var $page = $( e.target ),
+ scroll = $page.find(".ui-content").jqmData("scroll");
-( function ( $, window, document, undefined ) {
- $.widget( "tizen.splitview", $.mobile.widget, {
- options : {
- fixed : false,
- dividerVertical : true,
- ratio : [],
- initSelector : ":jqmData(role='splitview')"
- },
+ if ( scroll === "y" ) {
+ resizePageContentHeight( e.target );
+ }
+ });
- _create : function () {
- var self = this,
- $el = self.element,
- opt = self.options,
- $panes = $el.children( ".ui-pane" ),
- panesLength = $panes.length,
- spliters = [],
- spliterBars = [],
- ratioAttr = this.element.attr( "data-ratio" ),
- containerSize = [ 0, 0 ],
- resizeTimer = null,
- i = 0;
+}( jQuery, window, document ) );
- if ( panesLength !== 2 ) {
- if ( panesLength < 2 ) {
- for ( i = panesLength ; i < 2 ; ++i ) {
- self._addEmptyPanes();
- }
- } else {
- $panes.slice( 2 ).remove();
- }
- $panes = $el.children( ".ui-pane" );
- panesLength = $panes.length;
- }
- spliters[ 0 ] = $( "<a href='#' class='ui-spliter' aria-label='Drag scroll, double tap and move to adjust split area'></a>" ).insertAfter( $panes[ 0 ] );
- spliterBars[ 0 ] = $( "<div class='ui-spliter-bar'></div>" ).appendTo( spliters[ 0 ] );
- $( "<div class='ui-spliter-handle'></div>" ).appendTo( spliterBars[ 0 ] );
+ensureNS("jQuery.mobile.tizen.clrlib");
- $.extend( this, {
- moveTarget : null,
- moveData : {},
- spliters : spliters,
- spliterBars : spliterBars,
- panes : $panes,
- containerSize : containerSize,
- touchStatus : false,
- minPaneWidth : 50,
- savedRatio : []
- });
+jQuery.extend( jQuery.mobile.tizen.clrlib,
+{
+ nearestInt: function(val) {
+ var theFloor = Math.floor(val);
- self._bindTouchEvents();
- self._convertRatio( ratioAttr, $panes.length );
+ return (((val - theFloor) > 0.5) ? (theFloor + 1) : theFloor);
+ },
- $el.addClass( "ui-splitview ui-direction-" + self._direction( opt.dividerVertical ) );
+ /*
+ * Converts html color string to rgb array.
+ *
+ * Input: string clr_str, where
+ * clr_str is of the form "#aabbcc"
+ *
+ * Returns: [ r, g, b ], where
+ * r is in [0, 1]
+ * g is in [0, 1]
+ * b is in [0, 1]
+ */
+ HTMLToRGB: function(clr_str) {
+ clr_str = (('#' == clr_str.charAt(0)) ? clr_str.substring(1) : clr_str);
- self._refresh();
+ return ([
+ clr_str.substring(0, 2),
+ clr_str.substring(2, 4),
+ clr_str.substring(4, 6)
+ ].map(function(val) {
+ return parseInt(val, 16) / 255.0;
+ }));
+ },
- $( window ).unbind( ".splitview" )
- .bind( "pagechange.splitview resize.splitview", function ( event ) {
- $( ".ui-page-active .ui-splitview" ).each( function () {
- $( this ).data( "splitview" )._refresh();
- });
- });
- },
+ /*
+ * Converts rgb array to html color string.
+ *
+ * Input: [ r, g, b ], where
+ * r is in [0, 1]
+ * g is in [0, 1]
+ * b is in [0, 1]
+ *
+ * Returns: string of the form "#aabbcc"
+ */
+ RGBToHTML: function(rgb) {
+ return ("#" +
+ rgb.map(function(val) {
+ var ret = val * 255,
+ theFloor = Math.floor(ret);
- _addEmptyPanes : function () {
- var self = this,
- $el = self.element,
- opt = self.options,
- $panes = $el.children( ".ui-pane" ),
- scrollAttribute = ( $.support.scrollview ) ? "data-scroll='y'" : "",
- pane = $( "<div class='ui-pane' " + scrollAttribute + "></div>" );
+ ret = ((ret - theFloor > 0.5) ? (theFloor + 1) : theFloor);
+ ret = (((ret < 16) ? "0" : "") + (ret & 0xff).toString(16));
+ return ret;
+ })
+ .join(""));
+ },
- if ( scrollAttribute.length ) {
- pane.scrollview( { direction: "y" } );
- }
+ /*
+ * Converts hsl to rgb.
+ *
+ * From http://130.113.54.154/~monger/hsl-rgb.html
+ *
+ * Input: [ h, s, l ], where
+ * h is in [0, 360]
+ * s is in [0, 1]
+ * l is in [0, 1]
+ *
+ * Returns: [ r, g, b ], where
+ * r is in [0, 1]
+ * g is in [0, 1]
+ * b is in [0, 1]
+ */
+ HSLToRGB: function(hsl) {
+ var h = hsl[0] / 360.0, s = hsl[1], l = hsl[2];
- if ( !$panes.length ) {
- $el.append( pane );
- } else {
- $panes.last().after( pane );
- }
- },
+ if (0 === s)
+ return [ l, l, l ];
- _direction : function ( isHorizontal ) {
- return isHorizontal ? "horizontal" : "vertical";
- },
+ var temp2 = ((l < 0.5)
+ ? l * (1.0 + s)
+ : l + s - l * s),
+ temp1 = 2.0 * l - temp2,
+ temp3 = {
+ r: h + 1.0 / 3.0,
+ g: h,
+ b: h - 1.0 / 3.0
+ };
- _isStyleSpecified : function ( cssString ) {
- return ( typeof cssString !== "undefined" && cssString.length );
- },
+ temp3.r = ((temp3.r < 0) ? (temp3.r + 1.0) : ((temp3.r > 1) ? (temp3.r - 1.0) : temp3.r));
+ temp3.g = ((temp3.g < 0) ? (temp3.g + 1.0) : ((temp3.g > 1) ? (temp3.g - 1.0) : temp3.g));
+ temp3.b = ((temp3.b < 0) ? (temp3.b + 1.0) : ((temp3.b > 1) ? (temp3.b - 1.0) : temp3.b));
- _getContainerSize : function ( widthString, heightString ) {
- var self = this,
- $el = self.element,
- widthSpecified = self._isStyleSpecified( widthString ),
- heightSpecified = self._isStyleSpecified( heightString );
+ ret = [
+ (((6.0 * temp3.r) < 1) ? (temp1 + (temp2 - temp1) * 6.0 * temp3.r) :
+ (((2.0 * temp3.r) < 1) ? temp2 :
+ (((3.0 * temp3.r) < 2) ? (temp1 + (temp2 - temp1) * ((2.0 / 3.0) - temp3.r) * 6.0) :
+ temp1))),
+ (((6.0 * temp3.g) < 1) ? (temp1 + (temp2 - temp1) * 6.0 * temp3.g) :
+ (((2.0 * temp3.g) < 1) ? temp2 :
+ (((3.0 * temp3.g) < 2) ? (temp1 + (temp2 - temp1) * ((2.0 / 3.0) - temp3.g) * 6.0) :
+ temp1))),
+ (((6.0 * temp3.b) < 1) ? (temp1 + (temp2 - temp1) * 6.0 * temp3.b) :
+ (((2.0 * temp3.b) < 1) ? temp2 :
+ (((3.0 * temp3.b) < 2) ? (temp1 + (temp2 - temp1) * ((2.0 / 3.0) - temp3.b) * 6.0) :
+ temp1)))];
- self.containerSize[ 0 ] = ( widthSpecified ) ? $el.outerWidth( true ) : self._parentWidth();
- self.containerSize[ 1 ] = ( heightSpecified ) ? $el.outerHeight( true ) : self._parentHeight();
+ return ret;
+ },
- if ( !self.containerSize[ 0 ] || !self.containerSize[ 1 ] ) {
- return false;
- }
+ /*
+ * Converts hsv to rgb.
+ *
+ * Input: [ h, s, v ], where
+ * h is in [0, 360]
+ * s is in [0, 1]
+ * v is in [0, 1]
+ *
+ * Returns: [ r, g, b ], where
+ * r is in [0, 1]
+ * g is in [0, 1]
+ * b is in [0, 1]
+ */
+ HSVToRGB: function(hsv) {
+ return $.mobile.tizen.clrlib.HSLToRGB($.mobile.tizen.clrlib.HSVToHSL(hsv));
+ },
- return true;
- },
+ /*
+ * Converts rgb to hsv.
+ *
+ * from http://coecsl.ece.illinois.edu/ge423/spring05/group8/FinalProject/HSV_writeup.pdf
+ *
+ * Input: [ r, g, b ], where
+ * r is in [0, 1]
+ * g is in [0, 1]
+ * b is in [0, 1]
+ *
+ * Returns: [ h, s, v ], where
+ * h is in [0, 360]
+ * s is in [0, 1]
+ * v is in [0, 1]
+ */
+ RGBToHSV: function(rgb) {
+ var min, max, delta, h, s, v, r = rgb[0], g = rgb[1], b = rgb[2];
- _parentWidth : function () {
- var $parent = this.element.parent();
+ min = Math.min(r, Math.min(g, b));
+ max = Math.max(r, Math.max(g, b));
+ delta = max - min;
- if ( !$parent && typeof $parent === "undefined" && !$parent.length ) {
- return $( window ).width();
- }
+ h = 0;
+ s = 0;
+ v = max;
- return $parent.width();
- },
+ if (delta > 0.00001) {
+ s = delta / max;
- _parentHeight : function () {
- var $parent = this.element.parent(),
- heightString = "",
- heightSpecified = false,
- parentHeight = 0;
+ if (r === max)
+ h = (g - b) / delta ;
+ else
+ if (g === max)
+ h = 2 + (b - r) / delta ;
+ else
+ h = 4 + (r - g) / delta ;
- while ( $parent && typeof $parent !== "undefined" && $parent.length ) {
- if ( typeof $parent[ 0 ].style !== "undefined" ) {
- heightString = $parent[ 0 ].style.height;
- heightSpecified = ( typeof heightString !== "undefined" && heightString.length );
- if ( heightSpecified ) {
- parentHeight = $parent.height();
- break;
- }
- }
+ h *= 60 ;
- $parent = $parent.parent();
- }
+ if (h < 0)
+ h += 360 ;
+ }
- if ( !heightSpecified ) {
- parentHeight = $(window).height();
- }
+ return [h, s, v];
+ },
- return parentHeight;
- },
+ /*
+ * Converts hsv to hsl.
+ *
+ * Input: [ h, s, v ], where
+ * h is in [0, 360]
+ * s is in [0, 1]
+ * v is in [0, 1]
+ *
+ * Returns: [ h, s, l ], where
+ * h is in [0, 360]
+ * s is in [0, 1]
+ * l is in [0, 1]
+ */
+ HSVToHSL: function(hsv) {
+ var max = hsv[2],
+ delta = hsv[1] * max,
+ min = max - delta,
+ sum = max + min,
+ half_sum = sum / 2,
+ s_divisor = ((half_sum < 0.5) ? sum : (2 - max - min));
- _convertRatio : function ( ratioParam, panesLength ) {
- var self = this,
- ratio = [],
- loop = 0,
- type = typeof ratioParam,
- ratioArray = null,
- i;
+ return [ hsv[0], ((0 == s_divisor) ? 0 : (delta / s_divisor)), half_sum ];
+ },
- for ( i = 0; i < panesLength; ++i ) {
- ratio.push( 0 );
- }
+ /*
+ * Converts rgb to hsl
+ *
+ * Input: [ r, g, b ], where
+ * r is in [0, 1]
+ * g is in [0, 1]
+ * b is in [0, 1]
+ *
+ * Returns: [ h, s, l ], where
+ * h is in [0, 360]
+ * s is in [0, 1]
+ * l is in [0, 1]
+ */
+ RGBToHSL: function(rgb) {
+ return $.mobile.tizen.clrlib.HSVToHSL($.mobile.tizen.clrlib.RGBToHSV(rgb));
+ }
+});
- switch ( type ) {
- case "number":
- if ( panesLength ) {
- ratio[ 0 ] = ratioParam;
- }
- break;
- case "string":
- ratioArray = ratioParam.split( "," );
- loop = Math.min( ratioArray.length, panesLength );
- for ( i = 0; i < loop; ++i ) {
- ratio[ i ] = parseFloat( ratioArray[ i ] );
- }
- break;
- case "object":
- if ( !$.isArray( ratioParam ) ) {
- break;
- }
+/* ***************************************************************************
+ Flora License
- loop = Math.min( ratioParam.length, panesLength );
- for ( i = 0; i < loop; ++i ) {
- type = typeof ratioParam[ i ];
- ratio[ i ] = ( type === "string" ) ? parseFloat( ratioParam[ i ] ) :
- ( type === "number" ) ? ratioParam[ i ] : 0;
- }
- break;
- }
+ Version 1.1, April, 2013
- self.options.ratio = ratio;
- self._adjustRatio( panesLength );
- },
+ http://floralicense.org/license/
- _adjustRatio : function ( panesLength ) {
- var self = this,
- ratio = self.options.ratio,
- sum = 0,
- remain = 0,
- value = 0,
- subValue = 0,
- subRemain = 0,
- i;
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
- if ( !panesLength ) {
- self.options.ratio = [];
- return;
- }
+ 1. Definitions.
- for ( i in ratio ) {
- sum += ratio[ i ];
- }
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
- if ( sum !== 1 ) {
- remain = 1 - sum;
- value = remain / panesLength;
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
- for ( i in ratio ) {
- if ( value >= 0 ) {
- ratio[ i ] += value;
- remain = Math.max( 0, remain - value );
- } else {
- subRemain += value;
- subValue = Math.max( subRemain, ratio[ i ] * -1 );
- ratio[ i ] = Math.max( 0, ratio[ i ] + subValue );
- remain = Math.min( 0, remain - subValue );
- subRemain -= subValue;
- }
- }
+ "Legal Entity" shall mean the union of the acting entity and
+ all other entities that control, are controlled by, or are
+ under common control with that entity. For the purposes of
+ this definition, "control" means (i) the power, direct or indirect,
+ to cause the direction or management of such entity,
+ whether by contract or otherwise, or (ii) ownership of fifty percent (50%)
+ or more of the outstanding shares, or (iii) beneficial ownership of
+ such entity.
- if ( remain ) {
- if ( remain > 0 ) {
- ratio[ ratio.length - 1 ] += remain;
- } else {
- for ( i = ratio.length - 1; i >= 0; --i ) {
- subValue = Math.max( remain, ratio[ i ] * -1 );
- ratio[ i ] = Math.max( 0, ratio[ i ] + subValue );
- remain = Math.min( 0, remain - subValue );
- if ( !remain ) {
- break;
- }
- }
- }
- }
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
- self.options.ratio = ratio;
- }
- },
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation source,
+ and configuration files.
- _setOption : function ( key, value ) {
- var self = this,
- orgValue = self.options[ key ];
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
- if ( orgValue === value ) {
- return;
- }
+ "Work" shall mean the work of authorship, whether in Source or Object form,
+ made available under the License, as indicated by a copyright notice
+ that is included in or attached to the work (an example is provided
+ in the Appendix below).
- $.Widget.prototype._setOption.apply( this, arguments );
+ "Derivative Works" shall mean any work, whether in Source or Object form,
+ that is based on (or derived from) the Work and for which the editorial
+ revisions, annotations, elaborations, or other modifications represent,
+ as a whole, an original work of authorship. For the purposes of this License,
+ Derivative Works shall not include works that remain separable from,
+ or merely link (or bind by name) to the interfaces of, the Work and
+ Derivative Works thereof.
- switch ( key ) {
- case "fixed":
- self._fixed( value );
- break;
+ "Contribution" shall mean any work of authorship, including the original
+ version of the Work and any modifications or additions to that Work or
+ Derivative Works thereof, that is intentionally submitted to Licensor
+ for inclusion in the Work by the copyright owner or by an individual or
+ Legal Entity authorized to submit on behalf of the copyright owner.
+ For the purposes of this definition, "submitted" means any form of
+ electronic, verbal, or written communication sent to the Licensor or
+ its representatives, including but not limited to communication on
+ electronic mailing lists, source code control systems, and issue
+ tracking systems that are managed by, or on behalf of, the Licensor
+ for the purpose of discussing and improving the Work, but excluding
+ communication that is conspicuously marked or otherwise designated
+ in writing by the copyright owner as "Not a Contribution."
- case "dividerVertical":
- self._dividerVertical( value );
- break;
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
- case "ratio":
- self._ratio( value );
- break;
- }
- },
+ "Tizen Certified Platform" shall mean a software platform that complies
+ with the standards set forth in the Tizen Compliance Specification
+ and passes the Tizen Compliance Tests as defined from time to time
+ by the Tizen Technical Steering Group and certified by the Tizen
+ Association or its designated agent.
- _subtractDiffWidth : function ( width, diff ) {
- var self = this;
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
- if ( width <= self.minPaneWidth ) {
- return {
- width: width,
- diff: diff
- };
- }
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work
+ solely as incorporated into a Tizen Certified Platform, where such
+ license applies only to those patent claims licensable by such
+ Contributor that are necessarily infringed by their Contribution(s)
+ alone or by combination of their Contribution(s) with the Work solely
+ as incorporated into a Tizen Certified Platform to which such
+ Contribution(s) was submitted. If You institute patent litigation
+ against any entity (including a cross-claim or counterclaim
+ in a lawsuit) alleging that the Work or a Contribution incorporated
+ within the Work constitutes direct or contributory patent infringement,
+ then any patent licenses granted to You under this License for that
+ Work shall terminate as of the date such litigation is filed.
- width += diff;
- if ( width >= self.minPaneWidth ) {
- return {
- width: width,
- diff: 0
- };
- }
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof pursuant to the copyright license
+ above, in any medium, with or without modifications, and in Source or
+ Object form, provided that You meet the following conditions:
- return {
- width: self.minPaneWidth,
- diff: width - self.minPaneWidth
- };
- },
+ 1. You must give any other recipients of the Work or Derivative Works
+ a copy of this License; and
+ 2. You must cause any modified files to carry prominent notices stating
+ that You changed the files; and
+ 3. You must retain, in the Source form of any Derivative Works that
+ You distribute, all copyright, patent, trademark, and attribution
+ notices from the Source form of the Work, excluding those notices
+ that do not pertain to any part of the Derivative Works; and
+ 4. If the Work includes a "NOTICE" text file as part of its distribution,
+ then any Derivative Works that You distribute must include a readable
+ copy of the attribution notices contained within such NOTICE file,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works, in at least one of the following places:
+ within a NOTICE text file distributed as part of the Derivative Works;
+ within the Source form or documentation, if provided along with the
+ Derivative Works; or, within a display generated by the Derivative Works,
+ if and wherever such third-party notices normally appear.
+ The contents of the NOTICE file are for informational purposes only
+ and do not modify the License.
- _initRatio : function ( fromFirstPane, panes, isHorizontal, availableWidth ) {
- var self = this,
- sum = 0,
- widths = [],
- diff = 0,
- panesLength = panes.length,
- ret,
- i;
+ You may add Your own attribution notices within Derivative Works
+ that You distribute, alongside or as an addendum to the NOTICE text
+ from the Work, provided that such additional attribution notices
+ cannot be construed as modifying the License. You may add Your own
+ copyright statement to Your modifications and may provide additional or
+ different license terms and conditions for use, reproduction, or
+ distribution of Your modifications, or for any such Derivative Works
+ as a whole, provided Your use, reproduction, and distribution of
+ the Work otherwise complies with the conditions stated in this License.
- panes.each( function ( i ) {
- var pane = $( this );
- widths.push( isHorizontal ? pane.width() : pane.height() );
- sum += widths[ i ];
- });
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
- diff = availableWidth - sum;
- if ( !diff ) {
- return widths;
- }
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
- if ( diff > 0 ) {
- widths[ fromFirstPane ? 0 : panesLength - 1 ] += diff;
- } else {
- if ( fromFirstPane ) {
- for ( i = 0; i < panesLength; ++i ) {
- ret = self._subtractDiffWidth( widths[ i ], diff );
- widths[ i ] = ret.width;
- diff = ret.diff;
- if ( !diff ) {
- break;
- }
- }
- } else {
- for ( i = panesLength - 1; i >= 0; --i ) {
- diff = self._subtractDiffWidth( widths[ i ], diff );
- widths[ i ] = ret.width;
- diff = ret.diff;
- if ( !diff ) {
- break;
- }
- }
- }
- }
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
- sum = 0;
- for ( i in widths ) {
- sum += widths[ i ];
- }
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
- for ( i in self.options.ratio ) {
- self.options.ratio[ i ] = widths[ i ] / sum;
- }
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
- return widths;
- },
+ END OF TERMS AND CONDITIONS
- _horizontalBoundary : function () {
- var self = this,
- $el = self.element;
+ APPENDIX: How to apply the Flora License to your work
- return $el.outerWidth( true ) - $el.width();
- },
+ To apply the Flora License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
- _verticalBoundary : function () {
- var self = this,
- $el = self.element;
+ Copyright [yyyy] [name of copyright owner]
- return $el.outerHeight( true ) - $el.height();
- },
+ Licensed under the Flora License, Version 1.1 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
- _boundary : function ( type ) {
- var self = this,
- $el = self.element,
- computedStyle = window.getComputedStyle( $el[ 0 ], null ),
- margin = parseFloat( computedStyle[ "margin" + type ] ),
- border = parseFloat( computedStyle[ "border" + type + "Width" ] ),
- padding = parseFloat( computedStyle[ "padding" + type ] );
+ http://floralicense.org/license/
- return {
- margin: margin,
- border: border,
- padding: padding
- };
- },
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
- _layout : function ( initRatio, fromFirstPane ) {
- var self = this,
- $el = self.element,
- opt = self.options,
- isHorizontal = opt.dividerVertical,
- $panes = self.panes,
- spliters = self.spliters,
- spliterBars = self.spliterBars,
- spliterBar = self.spliterBars.length ? $( spliterBars[ 0 ] ) : null,
- spliterWidth = !spliterBar ? 0 :
- isHorizontal ? spliterBar.outerWidth() :
- spliterBar.outerHeight(),
- spliterBarMargin = !spliterBar ? 0 :
- isHorizontal ?
- spliterBar.outerWidth( true ) - spliterBar.outerWidth() :
- spliterBar.outerHeight( true ) - spliterBar.outerHeight(),
- panesLength = $panes.length,
- currentAvailable = 0,
- spliterSize = spliterWidth * ( panesLength - 1 ),
- parentWidth = self.containerSize[ 0 ],
- parentHeight = self.containerSize[ 1 ],
- width = parentWidth - self._horizontalBoundary(),
- height = parentHeight - self._verticalBoundary(),
- innerSize = isHorizontal ? height : width,
- availableWidth = isHorizontal ? width - spliterSize :
- height - spliterSize,
- initializedWidth = [],
- widthSum = 0,
- childSplitview = null;
+ * Author: Minkyu Kang <mk7.kang@samsung.com>
+ */
+
+/*
+ * Pinch Event
+ *
+ * Events
+ * pinchstart: triggered when start the touched two points
+ * pinch: triggered when move the touch point after pinchstart event occured
+ * pinchend: triggered when touchend event after pinchstart event occured
+ *
+ * Parameters
+ * point: touched points
+ * ratio: origin point-to-current point ratio for moving distance
+ *
+ * $("#pinch").bind("pinch", function (e, p) {
+ * console.log("point[0].x: " + p.point[0].x);
+ * console.log("point[0].y: " + p.point[0].y);
+ * console.log("point[1].x: " + p.point[1].x);
+ * console.log("point[1].y: " + p.point[1].y);
+ * console.log("ratio: " + p.ratio);
+ * });
+ *
+ * Options
+ * $.mobile.pinch.enabled: true or false
+ * $.mobile.pinch.min: minimum value of ratio
+ * $.mobile.pinch.max: maximum value of ratio
+ * $.mobile.pinch.factor: scale factor of ratio
+ * $.mobile.pinch.threshold: move threshold of ratio
+ * $.mobile.pinch.interval: interval for pinch event
+ */
- initRatio = !!initRatio;
- fromFirstPane = !!fromFirstPane;
- $el.css( {
- "min-width" : width,
- "min-height" : height
- });
+( function( $, window, undefined ) {
- if ( initRatio ) {
- initializedWidth = self._initRatio( fromFirstPane, $panes, isHorizontal, availableWidth );
- }
+pinch_event = {
+ setup: function () {
+ var thisObject = this,
+ $this = $( thisObject );
- currentAvailable = availableWidth;
- $panes.each( function ( i ) {
- var $pane = $( this ),
- paneWidth = initRatio ? initializedWidth[ i ] :
- Math.floor( availableWidth * self.options.ratio[i] ),
- prevPane = ( ( i ) ? $panes.eq( i - 1 ) : null ),
- posValue = 0,
- widthValue = 0,
- heightValue = 0,
- boundary = 0;
+ if ( !$.mobile.support.touch ) {
+ return;
+ }
- currentAvailable -= paneWidth;
- if ( i === ( panesLength - 1 ) ) {
- paneWidth = Math.max( Math.min( paneWidth, self.minPaneWidth ), paneWidth + currentAvailable );
- }
+ function getSize( point ) {
+ var x = point[0].x - point[1].x,
+ y = point[0].y - point[1].y;
- widthSum += paneWidth;
+ return Math.abs( x * y );
+ }
- if ( !prevPane ) {
- boundary = self._boundary( isHorizontal ? "Left" : "Top" );
- posValue = boundary.padding;
- } else {
- posValue = parseInt( prevPane.css( isHorizontal ? "left" : "top" ), 10 );
- posValue += isHorizontal ? prevPane.width() : prevPane.height();
- posValue += spliterWidth;
- }
+ function getParameter( point, ratio ) {
+ return { point: point, ratio: ratio };
+ }
- widthValue = isHorizontal ? paneWidth : innerSize;
- heightValue = isHorizontal ? innerSize : paneWidth;
+ $this.bind( "touchstart", function ( event ) {
+ var data = event.originalEvent.touches,
+ origin,
+ last_ratio = 1,
+ processing = false;
- $pane.css( {
- "width" : widthValue ,
- "height" : heightValue
- } );
+ if ( !$.mobile.pinch.enabled ) {
+ return;
+ }
- $pane.css( ( isHorizontal ? "left" : "top" ), posValue );
- });
+ if ( data.length != 2 ) {
+ return;
+ }
- $panes.each( function ( i ) {
- var $pane = $( this ),
- paneWidth = isHorizontal ? $pane.width() : $pane.height();
+ origin = [
+ { x: data[0].pageX, y: data[0].pageY },
+ { x: data[1].pageX, y: data[1].pageY }
+ ];
- self.options.ratio[ i ] = paneWidth / widthSum;
- });
+ $( event.target ).trigger( "pinchstart", getParameter( origin, undefined ) );
- $.each( spliters, function ( i ) {
- var spliter = $( this ),
- prevPane = $panes.eq( i ),
- bar = spliter.children( ".ui-spliter-bar" ),
- handle = bar.children( ".ui-spliter-handle" ),
- posValue = 0;
+ function pinchHandler( event ) {
+ var data = event.originalEvent.touches,
+ current,
+ ratio,
+ delta,
+ factor = $( window ).width() / $.mobile.pinch.factor;
- if ( isHorizontal ) {
- posValue = parseInt( prevPane.css( "left" ), 10 ) + prevPane.width() - spliterBarMargin;
- spliter.outerHeight( innerSize ).css( "left", posValue );
- } else {
- posValue = parseInt( prevPane.css( "top" ), 10 ) + prevPane.height() - spliterBarMargin;
- spliter.outerWidth( innerSize ).css( "top", posValue );
+ if ( processing ) {
+ return;
}
- if ( bar.length ) {
- bar[ isHorizontal ? "outerHeight" : "outerWidth" ]( innerSize );
- }
- if ( handle.length ) {
- handle.css( isHorizontal ? "top" : "left", ( innerSize - spliterWidth ) / 2 );
+ if ( !origin ) {
+ return;
}
- });
-
- childSplitview = $el.find( ".ui-splitview:first" );
- if ( !childSplitview.length ) {
- return;
- }
- childSplitview = childSplitview.data( "splitview" );
- if ( childSplitview ) {
- childSplitview._refresh();
- }
- },
-
- _bindTouchEvents : function () {
- var self = this,
- $el = self.element,
- $panes = self.panes,
- spliters = self.spliters;
+ current = [
+ { x: data[0].pageX, y: data[0].pageY },
+ { x: data[1].pageX, y: data[1].pageY }
+ ];
- $.each( spliters, function ( i ) {
- var spliter = $( this );
- self._bindSpliterTouchEvents.call( self, spliter );
- });
- },
+ delta = Math.sqrt( getSize( current ) / getSize( origin ) ) ;
+ if( delta ) {
+ ratio = delta;
+ }
- _bindSpliterTouchEvents : function ( spliter ) {
- var self = this,
- $el = self.element,
- opt = self.options,
- touchStartEvt = ( $.support.touch ? "touchstart" : "mousedown" ),
- touchMoveEvt = ( $.support.touch ? "touchmove" : "mousemove" ) + ".splitview",
- touchEndEvt = ( $.support.touch ? "touchend" : "mouseup" ) + ".splitview";
+ if ( ratio < $.mobile.pinch.min ) {
+ ratio = $.mobile.pinch.min;
+ } else if ( ratio > $.mobile.pinch.max ) {
+ ratio = $.mobile.pinch.max;
+ }
- spliter.bind( touchStartEvt, { e : spliter }, function ( event ) {
- if ( self.options.fixed ) {
+ if ( Math.abs( ratio - last_ratio ) < $.mobile.pinch.threshold ) {
return;
}
- var realEvent = $.support.touch ? event.originalEvent.changedTouches[0] : event,
- targetSpliter = event.data.e,
- prevPane = targetSpliter.prev(),
- nextPane = targetSpliter.next(),
- splitviewInPrev = prevPane.find( ".ui-splitview:first" ),
- splitviewInNext = nextPane.find( ".ui-splitview:first" ),
- isHorizontal = opt.dividerVertical,
- spliterWidth = isHorizontal ?
- $( self.spliterBars[0] ).outerWidth() :
- $( self.spliterBars[0] ).outerHeight();
+ $( event.target ).trigger( "pinch", getParameter( current, ratio ) );
- self.moveTarget = targetSpliter;
- self.moveData = {
- spliterWidth : spliterWidth || 0,
- prevPane : prevPane,
- nextPane : nextPane,
- splitviewInPrev : splitviewInPrev,
- splitviewInNext : splitviewInNext,
- prevPanePos : parseInt( prevPane.css( isHorizontal ? "left" : "top" ), 10 ) || 0,
- prevPaneWidth : parseInt( prevPane.css( isHorizontal ? "width" : "height" ), 10 ) || 0,
- nextPanePos : parseInt( nextPane.css( isHorizontal ? "left" : "top" ), 10 ) || 0,
- nextPaneWidth : parseInt( nextPane.css( isHorizontal ? "width" : "height" ), 10 ) || 0,
- targetPos : parseInt( targetSpliter.css( isHorizontal ? "left" : "top" ), 10 ) || 0,
- pagePos : isHorizontal ? realEvent.pageX : realEvent.pageY
- };
+ last_ratio = ratio;
- targetSpliter.addClass( "ui-spliter-active" );
+ if ( $.mobile.pinch.interval ) {
+ processing = true;
- $el.bind( touchMoveEvt, function ( event ) {
- if ( !self.touchStatus ) {
- return;
- }
- event.stopPropagation();
- self._drag( $.support.touch ? event.originalEvent.changedTouches[0] : event );
- }).bind( touchEndEvt, function ( event ) {
- event.stopPropagation();
- self._stop( $.support.touch ? event.originalEvent.changedTouches[0] : event );
- self.touchStatus = false;
- $el.unbind( ".splitview" );
- $( document ).unbind( ".splitview" );
- });
+ setTimeout( function () {
+ processing = false;
+ }, $.mobile.pinch.interval );
+ }
+ }
- $( document ).bind( touchMoveEvt + " " + touchEndEvt, function() {
- $el.trigger( touchEndEvt );
+ $this.bind( "touchmove", pinchHandler )
+ .one( "touchend", function ( event ) {
+ $this.unbind( "touchmove", pinchHandler );
+ $( event.target ).trigger( "pinchend",
+ getParameter( undefined, last_ratio ) );
+
+ origin = undefined;
+ current = undefined;
+ last_ratio = 1;
+ processing = false;
});
+ });
+ }
+};
- event.preventDefault();
- self.touchStatus = true;
- });
- },
+$.event.special["pinch"] = pinch_event;
- _drag : function ( e ) {
- if ( !this.moveData || typeof this.moveData === "undefined" ) {
- return;
- }
+$.mobile.pinch = {
+ enabled: true,
+ min: 0.1,
+ max: 3,
+ factor: 4,
+ threshold: 0.01,
+ interval: 50
+};
+
+})( jQuery, this );
- var self = this,
- $el = self.element,
- opt = self.options,
- isHorizontal = opt.dividerVertical,
- moveData = self.moveData,
- moveTarget = self.moveTarget,
- prevPane = moveData.prevPane,
- nextPane = moveData.nextPane,
- splitviewInPrev = moveData.splitviewInPrev,
- splitviewInNext = moveData.splitviewInNext,
- spliterWidth = moveData.spliterWidth,
- movement = null,
- targetPos = null,
- nextPanePos = null,
- prevPaneWidth = null,
- nextPaneWidth = null,
- pagePos = isHorizontal ? e.pageX : e.pageY,
- splitview = null;
- movement = pagePos - moveData.pagePos;
- if ( movement > 0 ) {
- movement = Math.min( Math.max( moveData.nextPaneWidth - self.minPaneWidth, 0 ), movement );
- } else {
- movement = Math.max( Math.max( moveData.prevPaneWidth - self.minPaneWidth, 0 ) * -1, movement );
- }
- nextPanePos = moveData.nextPanePos + movement;
- prevPaneWidth = Math.max( moveData.prevPaneWidth + movement, 0 );
- nextPaneWidth = Math.max( moveData.nextPaneWidth - movement, 0 );
- targetPos = moveData.targetPos + movement;
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Author: Sanghee Lee <sang-hee.lee@samsung.com>
+*/
- moveTarget.css( isHorizontal ? { left : targetPos } : { top : targetPos } );
- prevPane.css( isHorizontal ? { width : prevPaneWidth } : { height : prevPaneWidth } );
- nextPane.css( isHorizontal ? { width : nextPaneWidth, left : nextPanePos } :
- { height : nextPaneWidth, top : nextPanePos } );
+/**
+ * Splitview is a widget which can show different HTML contents at the same time on each divided pane.
+ * A user can place Splitview controls on JQuery Mobile's Content area and arrange two panes on the widget.
+ * And HTML fragments or another Splitview also can be placed on the pane.
+ * The number of panes inside of Splitview is restricted as two.
+ * If a user define only one pane in Splitview, a empty pane will be added automatically,
+ * on the other hand, if 3 or more panes are defined in Splitview, the panes after two will be ignored and removed from the DOM tree.
+ * The HTML fragments of a pane should be composed of elements describing a part of Web page (e.g. <div>...</div>).
+ * Also widgets can be included in the HTML fragments.
+ *
+ * HTML Attributes:
+ *
+ * data-fixed : The resizing mode of panes - fixed and flexible mode.
+ * If the value is true, the panes' sizes will be fixed, or if not, it will be flexible. (Default : false)
+ * data-divider-vertical : The direction of dividers.
+ * If the value is true, the panes will be placed in horizontal direction,
+ * or if not, it will be placed in vertical direction. (Default : "true")
+ * data-ratio : The ratio of two panes' widths or heights. (Default : [ 1/2, 1/2 ]
+ *
+ * APIs:
+ *
+ * pane ( id [ , element ] )
+ * : This method replaces child contents of a pane indicated by id attribute with contents of inputted element.
+ * If second argument is not specified, it will act as a getter method.
+ * The string of id has to be started with "#" which means "id" of CSS selectors.
+ * maximize ( id )
+ * : This method maximizes a pane's size indicated by id.
+ * The string of id has to be started with "#" which means "id" of CSS selectors.
+ * restore ()
+ * : This method restores all panes' sizes to the ratio prior to maximization.
+ *
+ * Examples:
+ *
+ * <div data-role="splitview" data-fixed="false" data-divider-vertical="true" data-ratio="0.5, 0.5">
+ * <div class="ui-pane">pane0</div>
+ * <div class="ui-pane">pane1</div>
+ * </div>
+ *
+ */
- if ( splitviewInPrev.length ) {
- splitview = splitviewInPrev.data( "splitview" );
- splitview._refresh( true, false );
- }
- if ( splitviewInNext.length ) {
- splitview = splitviewInNext.data( "splitview" );
- splitview._refresh( true, true );
- }
- },
+/**
+ @class Splitview
+ Splitview widget enables a user to place and arrange several panes. Each divided pane can show repective HTML contents.
- _stop : function ( e ) {
- if ( !this.moveData || !this.moveTarget ) {
- return;
- }
+ To add a Splitview widget to the application, use the following code:
- var self = this,
- $el = self.element,
- opt = self.options,
- $panes = self.panes,
- panesLength = $panes.length,
- isHorizontal = opt.dividerVertical,
- moveData = self.moveData,
- moveTarget = self.moveTarget,
- prevPane = moveData.prevPane,
- nextPane = moveData.nextPane,
- splitviewInPrev = moveData.splitviewInPrev,
- splitviewInNext = moveData.splitviewInNext,
- spliterWidth = moveData.spliterWidth,
- spliterSize = spliterWidth * ( panesLength - 1 ),
- movement = null,
- targetPos = null,
- nextPanePos = null,
- prevPaneWidth = null,
- nextPaneWidth = null,
- displayStyle = $el.css( "display" ),
- parentWidth = self.containerSize[ 0 ],
- parentHeight = self.containerSize[ 1 ],
- width = parentWidth - self._horizontalBoundary(),
- height = parentHeight - self._verticalBoundary(),
- availableWidth = isHorizontal ?
- ( width - spliterSize ) :
- ( height - spliterSize ),
- sum = 0;
+ <div data-role="splitview" data-fixed="false" data-divider-vertical="true" data-ratio="0.5, 0.5">
+ <div class="ui-pane">pane0</div>
+ <div class="ui-pane">pane1</div>
+ </div>
+*/
- moveTarget.removeClass( "ui-spliter-active" );
+/**
+ @property {Boolean} data-fixed
+ The resizing mode of panes - fixed and flexible mode.
+*/
- // ratio calculation
- $panes.each( function ( i ) {
- var $pane = $( this ),
- paneWidth = isHorizontal ? $pane.width() : $pane.height();
+/**
+ @property {Boolean} data-divider-vertical
+ The direction of dividers - horizontal or vertical.
+ */
- sum += paneWidth;
- });
+/**
+ @property {Array} data-ratio
+ The ratio of two panes' widths or heights.
+*/
- $panes.each( function ( i ) {
- var $pane = $( this ),
- paneWidth = isHorizontal ? $pane.width() : $pane.height();
+/**
+ @method pane
+ This method replaces child contents of a pane indicated by id attribute with contents of inputted element.
+ If second argument is not specified, it will act as a getter method.
- self.options.ratio[ i ] = paneWidth / sum;
- });
+ <div data-role="splitview">
+ <div class="ui-pane" id="pane0">pane0</div>
+ <div class="ui-pane" id="pane1">pane1</div>
+ </div>
+ $(".selector").splitview("pane", id, element);
+*/
- self.moveData = null;
- },
+/**
+ @method maximize
+ This method maximizes a pane's size indicated by id.
- _fixed : function ( isFix ) {
- var self = this,
- spliters = self.spliters;
+ <div data-role="splitview">
+ <div class="ui-pane" id="pane0">pane0</div>
+ <div class="ui-pane" id="pane1">pane1</div>
+ </div>
+ $(".selector").splitview("maximize", id);
+*/
- $.each( spliters, function ( i ) {
- var $spliter = $( this );
+/**
+ @method restore
+ This method restores all panes' sizes to the ratio prior to maximization.
- if ( isFix ) {
- $spliter.addClass( "ui-fixed" );
- } else {
- $spliter.removeClass( "ui-fixed" );
- }
- });
+ <div data-role="splitview">
+ <div class="ui-pane" id="pane0">pane0</div>
+ <div class="ui-pane" id="pane1">pane1</div>
+ </div>
+ $(".selector").splitview("restore");
+*/
- self._layout();
+( function ( $, window, document, undefined ) {
+ $.widget( "tizen.splitview", $.mobile.widget, {
+ options : {
+ fixed : false,
+ dividerVertical : true,
+ ratio : [],
+ initSelector : ":jqmData(role='splitview')"
},
- _dividerVertical : function ( isDividerVertical ) {
+ _create : function () {
var self = this,
$el = self.element,
- isHorizontal = isDividerVertical,
- $panes = null,
- $spliters = null,
- $bar = null,
- $handle = null;
-
- $panes = $el.children( ".ui-pane" );
- $spliters = $el.children( ".ui-spliter" );
- $bar = $spliters.children( ".ui-spliter-bar" );
- $handle = $bar.children( ".ui-spliter-handle" );
+ opt = self.options,
+ $panes = $el.children( ".ui-pane" ),
+ panesLength = $panes.length,
+ spliters = [],
+ spliterBars = [],
+ ratioAttr = this.element.attr( "data-ratio" ),
+ containerSize = [ 0, 0 ],
+ resizeTimer = null,
+ i = 0;
- $el.removeClass( "ui-direction-vertical" );
- $el.removeClass( "ui-direction-horizontal" );
- $el.addClass( "ui-splitview ui-direction-" + self._direction( isHorizontal ) );
+ if ( panesLength !== 2 ) {
+ if ( panesLength < 2 ) {
+ for ( i = panesLength ; i < 2 ; ++i ) {
+ self._addEmptyPanes();
+ }
+ } else {
+ $panes.slice( 2 ).remove();
+ }
- $panes.css( {
- "left" : "",
- "top" : "",
- "width" : "",
- "height" : ""
- });
+ $panes = $el.children( ".ui-pane" );
+ panesLength = $panes.length;
+ }
- $spliters.css( {
- "left" : "",
- "top" : "",
- "width" : "",
- "height" : ""
- });
+ spliters[ 0 ] = $( "<a href='#' class='ui-spliter' aria-label='Drag scroll, double tap and move to adjust split area'></a>" ).insertAfter( $panes[ 0 ] );
+ spliterBars[ 0 ] = $( "<div class='ui-spliter-bar'></div>" ).appendTo( spliters[ 0 ] );
+ $( "<div class='ui-spliter-handle'></div>" ).appendTo( spliterBars[ 0 ] );
- $bar.css( {
- "width" : "",
- "height" : ""
+ $.extend( this, {
+ moveTarget : null,
+ moveData : {},
+ spliters : spliters,
+ spliterBars : spliterBars,
+ panes : $panes,
+ containerSize : containerSize,
+ touchStatus : false,
+ minPaneWidth : 50,
+ savedRatio : []
});
- $handle.css( {
- "left" : "",
- "top" : ""
- });
+ self._bindTouchEvents();
+ self._convertRatio( ratioAttr, $panes.length );
- if ( self._getContainerSize( $el[ 0 ].style.width, $el[ 0 ].style.height ) ) {
- self._layout();
- }
- },
+ $el.addClass( "ui-splitview ui-direction-" + self._direction( opt.dividerVertical ) );
- _ratio : function ( ratioParam ) {
- var self = this,
- $el = self.element,
- $panes = $el.children( ".ui-pane" ),
- panesLength = $panes.length;
+ self._refresh();
- self._convertRatio( ratioParam, panesLength );
- self._layout();
+ $( window ).unbind( ".splitview" )
+ .bind( "pagechange.splitview resize.splitview", function ( event ) {
+ $( ".ui-page-active .ui-splitview" ).each( function () {
+ $( this ).data( "splitview" )._refresh();
+ });
+ });
},
- _refresh : function ( initRatio, fromFirstPane ) {
+ _addEmptyPanes : function () {
var self = this,
- $el = self.element;
+ $el = self.element,
+ opt = self.options,
+ $panes = $el.children( ".ui-pane" ),
+ scrollAttribute = ( $.support.scrollview ) ? "data-scroll='y'" : "",
+ pane = $( "<div class='ui-pane' " + scrollAttribute + "></div>" );
- initRatio = !!initRatio;
- fromFirstPane = !!fromFirstPane;
+ if ( scrollAttribute.length ) {
+ pane.scrollview( { direction: "y" } );
+ }
- if ( self._getContainerSize( $el[ 0 ].style.width, $el[ 0 ].style.height ) ) {
- self._layout( initRatio, fromFirstPane );
+ if ( !$panes.length ) {
+ $el.append( pane );
+ } else {
+ $panes.last().after( pane );
}
},
- pane : function ( id, element ) {
- if ( typeof id !== "string" ) {
- return null;
- }
+ _direction : function ( isHorizontal ) {
+ return isHorizontal ? "horizontal" : "vertical";
+ },
+
+ _isStyleSpecified : function ( cssString ) {
+ return ( typeof cssString !== "undefined" && cssString.length );
+ },
+ _getContainerSize : function ( widthString, heightString ) {
var self = this,
$el = self.element,
- $targetPane = $el.children( id ),
- $targetView = null,
- elementParent = null;
+ widthSpecified = self._isStyleSpecified( widthString ),
+ heightSpecified = self._isStyleSpecified( heightString );
- if ( !$targetPane.hasClass( "ui-pane" ) ) {
- return null;
- }
+ self.containerSize[ 0 ] = ( widthSpecified ) ? $el.outerWidth( true ) : self._parentWidth();
+ self.containerSize[ 1 ] = ( heightSpecified ) ? $el.outerHeight( true ) : self._parentHeight();
- // getter
- if ( !element ) {
- return $targetPane.contents();
+ if ( !self.containerSize[ 0 ] || !self.containerSize[ 1 ] ) {
+ return false;
}
- // setter
- if ( $targetPane.hasClass( "ui-scrollview-clip" ) ) {
- $targetPane.scrollview( "scrollTo", 0, 0, 0 );
+ return true;
+ },
- $targetView = $targetPane.children( ".ui-scrollview-view" );
- if ( !$targetView.length ) {
- return null;
- }
- } else {
- $targetView = $targetPane;
- }
+ _parentWidth : function () {
+ var $parent = this.element.parent();
- elementParent = element.parent();
- if ( elementParent.length && elementParent[ 0 ] === $targetView[ 0 ] ) {
- return;
+ if ( !$parent && typeof $parent === "undefined" && !$parent.length ) {
+ return $( window ).width();
}
- $targetView.empty().append( element ).trigger( "create" );
- $targetView.fadeIn( 'fast' );
+ return $parent.width();
},
- maximize : function ( id ) {
- if ( typeof id !== "string" ) {
- return;
- }
+ _parentHeight : function () {
+ var $parent = this.element.parent(),
+ heightString = "",
+ heightSpecified = false,
+ parentHeight = 0;
- var self = this,
- $el = self.element,
- $panes = self.panes,
- $targetPane = $el.children( id );
+ while ( $parent && typeof $parent !== "undefined" && $parent.length ) {
+ if ( typeof $parent[ 0 ].style !== "undefined" ) {
+ heightString = $parent[ 0 ].style.height;
+ heightSpecified = ( typeof heightString !== "undefined" && heightString.length );
+ if ( heightSpecified ) {
+ parentHeight = $parent.height();
+ break;
+ }
+ }
- if ( !$targetPane.hasClass( "ui-pane" ) ) {
- return;
+ $parent = $parent.parent();
}
- self.savedRatio = self.options.ratio.slice();
-
- self.options.ratio = [];
- $panes.each( function ( i ) {
- self.options.ratio.push( ( this === $targetPane[ 0 ] ) ? 1 : 0 );
- });
+ if ( !heightSpecified ) {
+ parentHeight = $(window).height();
+ }
- self._layout();
+ return parentHeight;
},
- restore : function () {
- var self = this;
+ _convertRatio : function ( ratioParam, panesLength ) {
+ var self = this,
+ ratio = [],
+ loop = 0,
+ type = typeof ratioParam,
+ ratioArray = null,
+ i;
- if ( !self.savedRatio.length ) {
- return;
+ for ( i = 0; i < panesLength; ++i ) {
+ ratio.push( 0 );
}
- self.options.ratio = self.savedRatio.slice();
- self._adjustRatio( self.panes.length );
-
- self._layout();
- }
- });
-
- $( document ).bind( "pagecreate create", function ( e ) {
- $.tizen.splitview.prototype.enhanceWithin( e.target );
- });
-} ( jQuery, window, document ) );
-
-
-\r
-/**\r
- @class Checkbox\r
- The check box widget shows a list of options on the screen where one or more can be selected. Check boxes can be used in Tizen as described in the jQueryMobile documentation for check boxes.<br/> To add a check box widget to the application, use the following code:\r
-\r
- <input type="checkbox" name="mycheck" id="check-test" class="favorite" />\r
- <label for="check-test">Favorite</label>\r
- <input type="checkbox" name="check-favorite" id="check-test2" checked="checked" disabled="disabled" class="favorite" />\r
- <label for="check-test2">Favorite Checked, Disabled</label>\r
-\r
- The check box can define callbacks for events as described in the jQueryMobile documentation for check box events.\r
- You can use methods with the check box as described in the jQueryMobile documentation for check box methods.\r
-\r
-*/\r
-/**\r
- @property {String} class\r
- Defines the check box style. <br/> The default value is check. If the value is set to favorite, a star-shaped check box is created.\r
-*/\r
-\r
-
-
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Authors: Hyunsook Park <hyunsook.park@samsung.com>
- * Wonseop Kim <wonseop.kim@samsung.com>
-*/
+ switch ( type ) {
+ case "number":
+ if ( panesLength ) {
+ ratio[ 0 ] = ratioParam;
+ }
+ break;
-( function ( $, window, undefined ) {
- var HALF_PI = Math.PI / 2,
- DEFAULT_STEP = 0.001,
- MotionPath = {},
- vec3 = window.vec3,
- arcLength3d = function ( p0, p1 ) {
- var d = [ p1[0] - p0[0], p1[1] - p0[1], p1[2] - p0[2] ],
- value = Math.sqrt( d[0] * d[0] + d[1] * d[1] + d[2] * d[2] );
- return value;
- };
+ case "string":
+ ratioArray = ratioParam.split( "," );
+ loop = Math.min( ratioArray.length, panesLength );
+ for ( i = 0; i < loop; ++i ) {
+ ratio[ i ] = parseFloat( ratioArray[ i ] );
+ }
+ break;
- MotionPath.base = function () {};
- MotionPath.base.prototype = {
- points: [],
- step: DEFAULT_STEP,
- length: 0,
- levels: [],
- init: function ( data ) {},
- calculateLevel: function ( maxLevel ) {},
- calculateTotalLength: function () {},
- getPosition: function ( percent ) {},
- getPercent: function ( start, interval ) {},
- getAngle: function ( percent ) {}
- };
+ case "object":
+ if ( !$.isArray( ratioParam ) ) {
+ break;
+ }
- MotionPath.bezier2d = function () {};
- MotionPath.bezier2d.prototype = $.extend( true, {}, MotionPath.base.prototype, {
- init: function ( data ) {
- this.points = data.points;
- this.step = data.step || DEFAULT_STEP;
- this.length = this.calculateTotalLength();
- this.levels = this.calculateLevel( data.maxLevel ) || [];
+ loop = Math.min( ratioParam.length, panesLength );
+ for ( i = 0; i < loop; ++i ) {
+ type = typeof ratioParam[ i ];
+ ratio[ i ] = ( type === "string" ) ? parseFloat( ratioParam[ i ] ) :
+ ( type === "number" ) ? ratioParam[ i ] : 0;
+ }
+ break;
+ }
+
+ self.options.ratio = ratio;
+ self._adjustRatio( panesLength );
},
- calculateLevel: function ( maxLevel ) {
- var totalLength = this.length,
- interval = totalLength / maxLevel,
- levels = [],
+ _adjustRatio : function ( panesLength ) {
+ var self = this,
+ ratio = self.options.ratio,
+ sum = 0,
+ remain = 0,
+ value = 0,
+ subValue = 0,
+ subRemain = 0,
i;
- if ( !maxLevel ) {
- return null;
- }
-
- for ( i = 0; i < maxLevel; i += 1 ) {
- levels[maxLevel - i] = this.getPercent( 0, interval * i );
+ if ( !panesLength ) {
+ self.options.ratio = [];
+ return;
}
- return levels;
- },
-
- calculateTotalLength: function () {
- var step = this.step,
- current = this.getPosition( 0 ),
- last = current,
- length = 0,
- percent;
- for ( percent = step; percent <= 1; percent += step ) {
- current = this.getPosition( percent );
- length += arcLength3d( last, current );
- last = current;
+ for ( i in ratio ) {
+ sum += ratio[ i ];
}
- return length;
- },
- getPosition: function ( percent ) {
- var points = this.points,
- getValue = function ( p1, c1, c2, p2, t ) {
- return Math.pow(1 - t, 3) * p1 +
- 3 * t * Math.pow( 1 - t, 2 ) * c1 +
- 3 * Math.pow( t, 2 ) * ( 1 - t ) * c2 +
- Math.pow( t, 3 ) * p2;
- },
- result = [
- getValue( points[0][0], points[1][0], points[2][0], points[3][0], percent ),
- getValue( points[0][2], points[1][2], points[2][2], points[3][2], percent )
- ];
- return [ result[0], 0, result[1] ];
- },
+ if ( sum !== 1 ) {
+ remain = 1 - sum;
+ value = remain / panesLength;
- getPercent: function ( start, interval ) {
- var step = this.step,
- current = this.getPosition( start = start || 0 ),
- last = current,
- targetLength = start + interval,
- length = 0,
- percent;
+ for ( i in ratio ) {
+ if ( value >= 0 ) {
+ ratio[ i ] += value;
+ remain = Math.max( 0, remain - value );
+ } else {
+ subRemain += value;
+ subValue = Math.max( subRemain, ratio[ i ] * -1 );
+ ratio[ i ] = Math.max( 0, ratio[ i ] + subValue );
+ remain = Math.min( 0, remain - subValue );
+ subRemain -= subValue;
+ }
+ }
- for ( percent = start + step; percent <= 1; percent += step ) {
- current = this.getPosition( percent );
- length += arcLength3d( last, current );
- if ( length >= targetLength ) {
- return percent;
+ if ( remain ) {
+ if ( remain > 0 ) {
+ ratio[ ratio.length - 1 ] += remain;
+ } else {
+ for ( i = ratio.length - 1; i >= 0; --i ) {
+ subValue = Math.max( remain, ratio[ i ] * -1 );
+ ratio[ i ] = Math.max( 0, ratio[ i ] + subValue );
+ remain = Math.min( 0, remain - subValue );
+ if ( !remain ) {
+ break;
+ }
+ }
+ }
}
- last = current;
+
+ self.options.ratio = ratio;
}
- return 1;
},
- getAngle: function ( percent ) {
- var points = this.points,
- getTangent = function ( p1, c1, c2, p2, t ) {
- return 3 * t * t * ( -p1 + 3 * c1 - 3 * c2 + p2 ) + 6 * t * ( p1 - 2 * c1 + c2 ) + 3 * ( -p1 + c1 );
- },
- tx = getTangent( points[0][0], points[1][0], points[2][0], points[3][0], percent ),
- ty = getTangent( points[0][2], points[1][2], points[2][2], points[3][2], percent );
- return Math.atan2( tx, ty ) - HALF_PI;
- }
+ _setOption : function ( key, value ) {
+ var self = this,
+ orgValue = self.options[ key ];
- } );
+ if ( orgValue === value ) {
+ return;
+ }
- // clamped cubic B-spline curve
- // http://web.mit.edu/hyperbook/Patrikalakis-Maekawa-Cho/node17.html
- // http://www.cs.mtu.edu/~shene/COURSES/cs3621/NOTES/spline/B-spline/bspline-curve-coef.html
- MotionPath.bspline = function () {};
- MotionPath.bspline.prototype = $.extend( true, {}, MotionPath.base.prototype, {
- _degree: 3,
- _numberOfControls : 0,
- _knotVectors: [],
- _numberOfKnots: 0,
+ $.Widget.prototype._setOption.apply( this, arguments );
- init: function ( data ) {
- this.points = data.points;
- this.step = data.step || DEFAULT_STEP;
- this._numberOfPoints = this.points.length - 1;
- this._numberOfKnots = this._numberOfPoints + this._degree + 1;
+ switch ( key ) {
+ case "fixed":
+ self._fixed( value );
+ break;
- var deltaKnot = 1 / ( this._numberOfKnots - ( 2 * this._degree ) ),
- v = deltaKnot,
- i = 0;
+ case "dividerVertical":
+ self._dividerVertical( value );
+ break;
- while ( i <= this._numberOfKnots ) {
- if ( i <= this._degree ) {
- this._knotVectors.push( 0 );
- } else if ( i < this._numberOfKnots - this._degree + 1 ) {
- this._knotVectors.push( v );
- v += deltaKnot;
- } else {
- this._knotVectors.push( 1 );
- }
- i += 1;
+ case "ratio":
+ self._ratio( value );
+ break;
}
-
- this.length = this.calculateTotalLength();
- this.levels = this.calculateLevel( data.maxLevel ) || [];
},
- _Np: function ( percent, i, degree ) {
- var knots = this._knotVectors,
- A = 0,
- B = 0,
- denominator = 0,
- N0 = function ( percent, i ) {
- return ( ( knots[i] <= percent && percent < knots[i + 1] ) ? 1 : 0 );
- };
+ _subtractDiffWidth : function ( width, diff ) {
+ var self = this;
- if ( degree === 1 ) {
- A = N0( percent, i );
- B = N0( percent, i + 1 );
- } else {
- A = this._Np( percent, i, degree - 1 );
- B = this._Np( percent, i + 1, degree - 1 );
+ if ( width <= self.minPaneWidth ) {
+ return {
+ width: width,
+ diff: diff
+ };
}
- denominator = knots[i + degree] - knots[i];
- A *= ( denominator !== 0 ) ? ( ( percent - knots[i] ) / denominator ) : 0;
- denominator = knots[i + degree + 1] - knots[i + 1];
- B *= ( denominator !== 0 ) ? ( ( knots[i + degree + 1] - percent ) / denominator ) : 0;
+ width += diff;
+ if ( width >= self.minPaneWidth ) {
+ return {
+ width: width,
+ diff: 0
+ };
+ }
- return A + B;
+ return {
+ width: self.minPaneWidth,
+ diff: width - self.minPaneWidth
+ };
},
- calculateLevel: function ( maxLevel ) {
- var totalLength = this.length,
- interval = totalLength / maxLevel,
- levels = [],
+ _initRatio : function ( fromFirstPane, panes, isHorizontal, availableWidth ) {
+ var self = this,
+ sum = 0,
+ widths = [],
+ diff = 0,
+ panesLength = panes.length,
+ ret,
i;
- if ( !maxLevel ) {
- return null;
+ panes.each( function ( i ) {
+ var pane = $( this );
+ widths.push( isHorizontal ? pane.width() : pane.height() );
+ sum += widths[ i ];
+ });
+
+ diff = availableWidth - sum;
+ if ( !diff ) {
+ return widths;
+ }
+
+ if ( diff > 0 ) {
+ widths[ fromFirstPane ? 0 : panesLength - 1 ] += diff;
+ } else {
+ if ( fromFirstPane ) {
+ for ( i = 0; i < panesLength; ++i ) {
+ ret = self._subtractDiffWidth( widths[ i ], diff );
+ widths[ i ] = ret.width;
+ diff = ret.diff;
+ if ( !diff ) {
+ break;
+ }
+ }
+ } else {
+ for ( i = panesLength - 1; i >= 0; --i ) {
+ diff = self._subtractDiffWidth( widths[ i ], diff );
+ widths[ i ] = ret.width;
+ diff = ret.diff;
+ if ( !diff ) {
+ break;
+ }
+ }
+ }
}
- for ( i = 0; i < maxLevel; i += 1 ) {
- levels[maxLevel - i] = this.getPercent( 0, interval * i );
- }
- return levels;
+ sum = 0;
+ for ( i in widths ) {
+ sum += widths[ i ];
+ }
+
+ for ( i in self.options.ratio ) {
+ self.options.ratio[ i ] = widths[ i ] / sum;
+ }
+
+ return widths;
+ },
+
+ _horizontalBoundary : function () {
+ var self = this,
+ $el = self.element;
+
+ return $el.outerWidth( true ) - $el.width();
},
- calculateTotalLength: function () {
- var step = this.step,
- current = this.getPosition( 0 ),
- last = current,
- length = 0,
- percent;
- for ( percent = step; percent <= 1; percent += step ) {
- current = this.getPosition( percent );
- length += arcLength3d( last, current );
- last = current;
- }
- return length;
+ _verticalBoundary : function () {
+ var self = this,
+ $el = self.element;
+
+ return $el.outerHeight( true ) - $el.height();
},
- getPosition: function ( percent ) {
- var result = [], i, j, sum;
- percent = percent.toFixed( 4 );
- for ( j = 0; j < 3; j += 1 ) {
- sum = 0;
- for ( i = 0; i <= this._numberOfPoints; i += 1 ) {
- sum += this.points[i][j] * this._Np( percent, i, this._degree );
- }
- result[j] = sum;
- }
+ _boundary : function ( type ) {
+ var self = this,
+ $el = self.element,
+ computedStyle = window.getComputedStyle( $el[ 0 ], null ),
+ margin = parseFloat( computedStyle[ "margin" + type ] ),
+ border = parseFloat( computedStyle[ "border" + type + "Width" ] ),
+ padding = parseFloat( computedStyle[ "padding" + type ] );
- return result;
+ return {
+ margin: margin,
+ border: border,
+ padding: padding
+ };
},
- getPercent: function ( start, interval ) {
- var step = this.step,
- current = this.getPosition( start = start || 0 ),
- last = current,
- targetLength = start + interval,
- length = 0,
- percent;
+ _layout : function ( initRatio, fromFirstPane ) {
+ var self = this,
+ $el = self.element,
+ opt = self.options,
+ isHorizontal = opt.dividerVertical,
+ $panes = self.panes,
+ spliters = self.spliters,
+ spliterBars = self.spliterBars,
+ spliterBar = self.spliterBars.length ? $( spliterBars[ 0 ] ) : null,
+ spliterWidth = !spliterBar ? 0 :
+ isHorizontal ? spliterBar.outerWidth() :
+ spliterBar.outerHeight(),
+ spliterBarMargin = !spliterBar ? 0 :
+ isHorizontal ?
+ spliterBar.outerWidth( true ) - spliterBar.outerWidth() :
+ spliterBar.outerHeight( true ) - spliterBar.outerHeight(),
+ panesLength = $panes.length,
+ currentAvailable = 0,
+ spliterSize = spliterWidth * ( panesLength - 1 ),
+ parentWidth = self.containerSize[ 0 ],
+ parentHeight = self.containerSize[ 1 ],
+ width = parentWidth - self._horizontalBoundary(),
+ height = parentHeight - self._verticalBoundary(),
+ innerSize = isHorizontal ? height : width,
+ availableWidth = isHorizontal ? width - spliterSize :
+ height - spliterSize,
+ initializedWidth = [],
+ widthSum = 0,
+ childSplitview = null;
- for ( percent = start + step; percent <= 1; percent += step ) {
- current = this.getPosition( percent );
- length += arcLength3d( last, current );
- if ( length >= targetLength ) {
- return percent;
- }
- last = current;
+ initRatio = !!initRatio;
+ fromFirstPane = !!fromFirstPane;
+
+ $el.css( {
+ "min-width" : width,
+ "min-height" : height
+ });
+
+ if ( initRatio ) {
+ initializedWidth = self._initRatio( fromFirstPane, $panes, isHorizontal, availableWidth );
}
- return 1;
- },
- getAngle: function ( percent ) {
- var prev = this.getPosition( percent ),
- next = this.getPosition( percent + 0.001 ),
- dir = vec3.normalize( vec3.direction( prev, next ) ),
- cosValue = vec3.dot( dir, [1, 0, 0] );
+ currentAvailable = availableWidth;
+ $panes.each( function ( i ) {
+ var $pane = $( this ),
+ paneWidth = initRatio ? initializedWidth[ i ] :
+ Math.floor( availableWidth * self.options.ratio[i] ),
+ prevPane = ( ( i ) ? $panes.eq( i - 1 ) : null ),
+ posValue = 0,
+ widthValue = 0,
+ heightValue = 0,
+ boundary = 0;
- return Math.acos( cosValue ) + Math.PI;
- }
- } );
+ currentAvailable -= paneWidth;
+ if ( i === ( panesLength - 1 ) ) {
+ paneWidth = Math.max( Math.min( paneWidth, self.minPaneWidth ), paneWidth + currentAvailable );
+ }
- $.motionpath = function ( type, data ) {
- var object = new MotionPath[type]();
- object.init( data );
- return object;
- };
-} ( jQuery, window ) );
+ widthSum += paneWidth;
+ if ( !prevPane ) {
+ boundary = self._boundary( isHorizontal ? "Left" : "Top" );
+ posValue = boundary.padding;
+ } else {
+ posValue = parseInt( prevPane.css( isHorizontal ? "left" : "top" ), 10 );
+ posValue += isHorizontal ? prevPane.width() : prevPane.height();
+ posValue += spliterWidth;
+ }
+ widthValue = isHorizontal ? paneWidth : innerSize;
+ heightValue = isHorizontal ? innerSize : paneWidth;
-/****************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Author: Wongi Lee <wongi11.lee@samsung.com>
-*/
+ $pane.css( {
+ "width" : widthValue ,
+ "height" : heightValue
+ } );
-/**
- * Extendable List Widget for unlimited data.
- * To support more then 1,000 items, special list widget developed.
- * Fast initialize and append some element into the DOM tree repeatedly.
- * DB connection and works like DB cursor.
- *
- * HTML Attributes:
- *
- * data-role: extendablelist
- * data-template : jQuery.template ID that populate into extendable list. A button : a <DIV> element with "data-role : button" should be included on data-template.
- * data-dbtable : DB Table name. It used as window[DB NAME]. Loaded data should be converted as window object.
- * data-extenditems : Number of elements to extend at once.
- *
- * ID : <UL> element that has "data-role=extendablelist" must have ID attribute.
- * Class : <UL> element that has "data-role=extendablelist" should have "vlLoadSuccess" class to guaranty DB loading is completed.
- * tmp_load_more : Template ID for "load more" message and button.
- *
- *
- *APIs:
- * create ( {
- * itemData: function ( idx ) { return json_obj; },
- * numItemData: number or function () { return number; },
- * cacheItemData: function ( minIdx, maxIdx ) {}
- * } )
- * : Create a extendable list widget. At this moment, _create method is called.
- * args : A collection of options
- * itemData: A function that returns JSON object for given index. Mandatory.
- * numItemData: Total number of itemData. Mandatory.
- * cacheItemData: Extendable list will ask itemData between minIdx and maxIdx.
- * Developers can implement this function for preparing data.
- * Optional.
- *
- *Examples:
- *
- * <script id="tmp-3-1-1" type="text/x-jquery-tmpl">
- * <li class="ui-li-3-1-1"><span class="ui-li-text-main">${NAME}</span></li>
- * </script>
- *
- * <script id="tmp_load_more" type="text/x-jquery-tmpl">
- * <li class="ui-li-3-1-1" style="text-align:center; margin:0 auto">
- * <div data-role="button">Load ${NUM_MORE_ITEMS} more items</div>
- * </li>
- * </script>
- *
- * <ul id = "extendable_list_main" data-role="extendablelist" data-extenditems="50" data-template="tmp-3-1-1">
- * </ul>
- *
- */
+ $pane.css( ( isHorizontal ? "left" : "top" ), posValue );
+ });
-/**
- @class Extendablelist
- In the Web environment, it is challenging to display a large amount of data in a list, such as displaying a contact list of over 1000 list items. It takes time to display the entire list in HTML and the DOM manipulation is complex.
- The extendable list widget is used to display a list of unlimited data elements on the screen for better performance. The list is extended if you click the button at the bottom of the list to load more data elements. Extendable lists are based on the jQuery.template plugin as described in the jQuery documentation for jQuery.template plugin.<br/>
- To add a extendable list widget to the application, use the following code:
+ $panes.each( function ( i ) {
+ var $pane = $( this ),
+ paneWidth = isHorizontal ? $pane.width() : $pane.height();
- <script id="tmp-3-1-1" type="text/x-jquery-tmpl">
- <li class="ui-li-3-1-1"><span class="ui-li-text-main">${NAME}</span></li>
- </script>
- <script id="tmp_load_more" type="text/x-jquery-tmpl">
- <li class="ui-li-3-1-1" style="text-align:center; margin:0 auto">
- <div data-role="button">Load ${NUM_MORE_ITEMS} more items</div>
- </li>
- </script>
- <ul id="extendable_list_main" data-role="extendablelist" data-extenditems="50" data-template="tmp-3-1-1">
- </ul>
-*/
-/**
- @property {String} data-role
- Creates the extendable list view. The value must be set to extendablelist. Only the <ul> element, which a id attribute defined, supports this option. Also, the elLoadSuccess class attribute must be defined in the <ul> element to ensure that loading data from the database is complete.
-*/
-/**
- @property {String} data-template
- Specifies the jQuery.template element ID. The jQuery.template must be defined. The template style can use rem units to support scalability. For using the button at the bottom of the list to load more data elements, there must be list view template with the button. The attribute ID must be tmp_load_more.
-*/
-/**
- @property {Integer} data-extenditems
- Defines the number of data elements to be extended at a time.
-*/
-( function ( $, undefined ) {
+ self.options.ratio[ i ] = paneWidth / widthSum;
+ });
+
+ $.each( spliters, function ( i ) {
+ var spliter = $( this ),
+ prevPane = $panes.eq( i ),
+ bar = spliter.children( ".ui-spliter-bar" ),
+ handle = bar.children( ".ui-spliter-handle" ),
+ posValue = 0;
- //Keeps track of the number of lists per page UID
- //This allows support for multiple nested list in the same page
- //https://github.com/jquery/jquery-mobile/issues/1617
- var listCountPerPage = {};
+ if ( isHorizontal ) {
+ posValue = parseInt( prevPane.css( "left" ), 10 ) + prevPane.width() - spliterBarMargin;
+ spliter.outerHeight( innerSize ).css( "left", posValue );
+ } else {
+ posValue = parseInt( prevPane.css( "top" ), 10 ) + prevPane.height() - spliterBarMargin;
+ spliter.outerWidth( innerSize ).css( "top", posValue );
+ }
- $.widget( "tizen.extendablelist", $.mobile.widget, {
- options: {
- theme: "s",
- countTheme: "c",
- headerTheme: "b",
- dividerTheme: "b",
- splitIcon: "arrow-r",
- splitTheme: "b",
- inset: false,
- id: "", /* Extendable list UL elemet's ID */
- extenditems: 50, /* Number of append items */
- childSelector: " li", /* To support swipe list */
- dbtable: "",
- template : "", /* Template for each list item */
- loadmore : "tmp_load_more", /* Template for "Load more" message */
- scrollview: false,
- initSelector: ":jqmData(role='extendablelist')"
- },
+ if ( bar.length ) {
+ bar[ isHorizontal ? "outerHeight" : "outerWidth" ]( innerSize );
+ }
+ if ( handle.length ) {
+ handle.css( isHorizontal ? "top" : "left", ( innerSize - spliterWidth ) / 2 );
+ }
+ });
- _stylerMouseUp: function () {
- $( this ).addClass( "ui-btn-up-s" );
- $( this ).removeClass( "ui-btn-down-s" );
- },
+ childSplitview = $el.find( ".ui-splitview:first" );
+ if ( !childSplitview.length ) {
+ return;
+ }
- _stylerMouseDown: function () {
- $( this ).addClass( "ui-btn-down-s" );
- $( this ).removeClass( "ui-btn-up-s" );
+ childSplitview = childSplitview.data( "splitview" );
+ if ( childSplitview ) {
+ childSplitview._refresh();
+ }
},
- _stylerMouseOver: function () {
- $( this ).toggleClass( "ui-btn-hover-s" );
- },
+ _bindTouchEvents : function () {
+ var self = this,
+ $el = self.element,
+ $panes = self.panes,
+ spliters = self.spliters;
- _stylerMouseOut: function () {
- $( this ).toggleClass( "ui-btn-hover-s" );
- $( this ).addClass( "ui-btn-up-s" );
- $( this ).removeClass( "ui-btn-down-s" );
+ $.each( spliters, function ( i ) {
+ var spliter = $( this );
+ self._bindSpliterTouchEvents.call( self, spliter );
+ });
},
- _pushData: function ( template ) {
- var o = this.options,
- t = this,
- i = 0,
- myTemplate = $( "#" + template ),
- loadMoreItems = ( o.extenditems > t._numItemData - t._lastIndex ? t._numItemData - t.lastIndex : o.extenditems ),
- htmlData;
+ _bindSpliterTouchEvents : function ( spliter ) {
+ var self = this,
+ $el = self.element,
+ opt = self.options,
+ touchStartEvt = ( $.support.touch ? "touchstart" : "mousedown" ),
+ touchMoveEvt = ( $.support.touch ? "touchmove" : "mousemove" ) + ".splitview",
+ touchEndEvt = ( $.support.touch ? "touchend" : "mouseup" ) + ".splitview";
- for (i = 0; i < loadMoreItems; i++ ) {
- htmlData = myTemplate.tmpl( t._itemData( i ) );
- $( o.id ).append( $( htmlData ).attr( 'id', 'li_' + i ) );
+ spliter.bind( touchStartEvt, { e : spliter }, function ( event ) {
+ if ( self.options.fixed ) {
+ return;
+ }
- /* Add style */
- $( o.id + ">" + o.childSelector )
- .addClass( "ui-btn-up-s" )
- .bind( "mouseup", t._stylerMouseUp )
- .bind( "mousedown", t._stylerMouseDown )
- .bind( "mouseover", t._stylerMouseOver )
- .bind( "mouseout", t._stylerMouseOut );
+ var realEvent = $.support.touch ? event.originalEvent.changedTouches[0] : event,
+ targetSpliter = event.data.e,
+ prevPane = targetSpliter.prev(),
+ nextPane = targetSpliter.next(),
+ splitviewInPrev = prevPane.find( ".ui-splitview:first" ),
+ splitviewInNext = nextPane.find( ".ui-splitview:first" ),
+ isHorizontal = opt.dividerVertical,
+ spliterWidth = isHorizontal ?
+ $( self.spliterBars[0] ).outerWidth() :
+ $( self.spliterBars[0] ).outerHeight();
- t._lastIndex += 1;
- }
+ self.moveTarget = targetSpliter;
+ self.moveData = {
+ spliterWidth : spliterWidth || 0,
+ prevPane : prevPane,
+ nextPane : nextPane,
+ splitviewInPrev : splitviewInPrev,
+ splitviewInNext : splitviewInNext,
+ prevPanePos : parseInt( prevPane.css( isHorizontal ? "left" : "top" ), 10 ) || 0,
+ prevPaneWidth : parseInt( prevPane.css( isHorizontal ? "width" : "height" ), 10 ) || 0,
+ nextPanePos : parseInt( nextPane.css( isHorizontal ? "left" : "top" ), 10 ) || 0,
+ nextPaneWidth : parseInt( nextPane.css( isHorizontal ? "width" : "height" ), 10 ) || 0,
+ targetPos : parseInt( targetSpliter.css( isHorizontal ? "left" : "top" ), 10 ) || 0,
+ pagePos : isHorizontal ? realEvent.pageX : realEvent.pageY
+ };
- /* After push data, re-style extendable list widget */
- $( o.id ).trigger( "create" );
+ targetSpliter.addClass( "ui-spliter-active" );
+
+ $el.bind( touchMoveEvt, function ( event ) {
+ if ( !self.touchStatus ) {
+ return;
+ }
+ event.stopPropagation();
+ self._drag( $.support.touch ? event.originalEvent.changedTouches[0] : event );
+ }).bind( touchEndEvt, function ( event ) {
+ event.stopPropagation();
+ self._stop( $.support.touch ? event.originalEvent.changedTouches[0] : event );
+ self.touchStatus = false;
+ $el.unbind( ".splitview" );
+ $( document ).unbind( ".splitview" );
+ });
+
+ $( document ).bind( touchMoveEvt + " " + touchEndEvt, function() {
+ $el.trigger( touchEndEvt );
+ });
+
+ event.preventDefault();
+ self.touchStatus = true;
+ });
},
- _loadmore: function ( event ) {
- var t = event.data, // <li> element
- o = t.options,
- i = 0,
- myTemplate = $( "#" + o.template ),
- loadMoreItems = ( o.extenditems > t._numItemData - t._lastIndex ? t._numItemData - t._lastIndex : o.extenditems ),
- htmlData,
- more_items_to_load,
- num_next_load_items;
+ _drag : function ( e ) {
+ if ( !this.moveData || typeof this.moveData === "undefined" ) {
+ return;
+ }
- /* Remove load more message */
- $( "#load_more_message" ).remove();
+ var self = this,
+ $el = self.element,
+ opt = self.options,
+ isHorizontal = opt.dividerVertical,
+ moveData = self.moveData,
+ moveTarget = self.moveTarget,
+ prevPane = moveData.prevPane,
+ nextPane = moveData.nextPane,
+ splitviewInPrev = moveData.splitviewInPrev,
+ splitviewInNext = moveData.splitviewInNext,
+ spliterWidth = moveData.spliterWidth,
+ movement = null,
+ targetPos = null,
+ nextPanePos = null,
+ prevPaneWidth = null,
+ nextPaneWidth = null,
+ pagePos = isHorizontal ? e.pageX : e.pageY,
+ splitview = null;
- /* Append More Items */
- for ( i = 0; i < loadMoreItems; i++ ) {
- htmlData = myTemplate.tmpl( t._itemData( t._lastIndex ) );
- $( o.id ).append( $( htmlData ).attr( 'id', 'li_' + t._lastIndex ) );
- t._lastIndex += 1;
+ movement = pagePos - moveData.pagePos;
+ if ( movement > 0 ) {
+ movement = Math.min( Math.max( moveData.nextPaneWidth - self.minPaneWidth, 0 ), movement );
+ } else {
+ movement = Math.max( Math.max( moveData.prevPaneWidth - self.minPaneWidth, 0 ) * -1, movement );
}
- /* Append "Load more" message on the last of list */
- if ( t._numItemData > t._lastIndex ) {
- myTemplate = $( "#" + o.loadmore );
- more_items_to_load = t._numItemData - t._lastIndex;
- num_next_load_items = ( o.extenditems <= more_items_to_load ) ? o.extenditems : more_items_to_load;
- htmlData = myTemplate.tmpl( { NUM_MORE_ITEMS : num_next_load_items } );
- // Button minimum height(37px)
- $( o.id ).append( $( htmlData ).attr( 'id', "load_more_message" ).css( 'min-height' , "37px") );
+ nextPanePos = moveData.nextPanePos + movement;
+ prevPaneWidth = Math.max( moveData.prevPaneWidth + movement, 0 );
+ nextPaneWidth = Math.max( moveData.nextPaneWidth - movement, 0 );
+ targetPos = moveData.targetPos + movement;
+
+ moveTarget.css( isHorizontal ? { left : targetPos } : { top : targetPos } );
+ prevPane.css( isHorizontal ? { width : prevPaneWidth } : { height : prevPaneWidth } );
+ nextPane.css( isHorizontal ? { width : nextPaneWidth, left : nextPanePos } :
+ { height : nextPaneWidth, top : nextPanePos } );
+
+ if ( splitviewInPrev.length ) {
+ splitview = splitviewInPrev.data( "splitview" );
+ splitview._refresh( true, false );
}
- $( o.id ).trigger( "create" );
- $( o.id ).extendablelist( "refresh" );
+ if ( splitviewInNext.length ) {
+ splitview = splitviewInNext.data( "splitview" );
+ splitview._refresh( true, true );
+ }
},
- recreate: function ( newArray ) {
- this._create( {
- itemData: function ( idx ) { return newArray[ idx ]; },
- numItemData: newArray.length
- } );
- },
+ _stop : function ( e ) {
+ if ( !this.moveData || !this.moveTarget ) {
+ return;
+ }
- _initList: function (args ) {
- var t = this,
- o = this.options,
- myTemplate,
- more_items_to_load,
- num_next_load_items,
- htmlData;
+ var self = this,
+ $el = self.element,
+ opt = self.options,
+ $panes = self.panes,
+ panesLength = $panes.length,
+ isHorizontal = opt.dividerVertical,
+ moveData = self.moveData,
+ moveTarget = self.moveTarget,
+ prevPane = moveData.prevPane,
+ nextPane = moveData.nextPane,
+ splitviewInPrev = moveData.splitviewInPrev,
+ splitviewInNext = moveData.splitviewInNext,
+ spliterWidth = moveData.spliterWidth,
+ spliterSize = spliterWidth * ( panesLength - 1 ),
+ movement = null,
+ targetPos = null,
+ nextPanePos = null,
+ prevPaneWidth = null,
+ nextPaneWidth = null,
+ displayStyle = $el.css( "display" ),
+ parentWidth = self.containerSize[ 0 ],
+ parentHeight = self.containerSize[ 1 ],
+ width = parentWidth - self._horizontalBoundary(),
+ height = parentHeight - self._verticalBoundary(),
+ availableWidth = isHorizontal ?
+ ( width - spliterSize ) :
+ ( height - spliterSize ),
+ sum = 0;
- /* Make Gen list by template */
- if ( t._lastIndex <= 0 ) {
- t._pushData( o.template );
+ moveTarget.removeClass( "ui-spliter-active" );
- /* Append "Load more" message on the last of list */
- if ( t._numItemData > t._lastIndex ) {
- myTemplate = $( "#" + o.loadmore );
- more_items_to_load = t._numItemData - t._lastIndex;
- num_next_load_items = ( o.extenditems <= more_items_to_load) ? o.extenditems : more_items_to_load;
- htmlData = myTemplate.tmpl( { NUM_MORE_ITEMS : num_next_load_items } );
- // Button minimum height(37px)
- $( o.id ).append( $( htmlData ).attr( 'id', "load_more_message" ).css( 'min-height' , "37px") );
+ // ratio calculation
+ $panes.each( function ( i ) {
+ var $pane = $( this ),
+ paneWidth = isHorizontal ? $pane.width() : $pane.height();
- $( "#load_more_message" ).live( "click", t, t._loadmore );
- } else {
- /* No more items to load */
- $( "#load_more_message" ).die();
- $( "#load_more_message" ).remove();
- }
- }
+ sum += paneWidth;
+ });
- if ( o.childSelector == " ul" ) {
- $( o.id + " ul" ).swipelist();
- }
+ $panes.each( function ( i ) {
+ var $pane = $( this ),
+ paneWidth = isHorizontal ? $pane.width() : $pane.height();
- $( o.id ).trigger( "create" );
+ self.options.ratio[ i ] = paneWidth / sum;
+ });
- t.refresh( true );
+ self.moveData = null;
},
- create: function () {
- var o = this.options;
+ _fixed : function ( isFix ) {
+ var self = this,
+ spliters = self.spliters;
- /* external API for AJAX callback */
- this._create.apply( this, arguments );
- },
+ $.each( spliters, function ( i ) {
+ var $spliter = $( this );
- _create: function ( args ) {
- var t = this,
- o = this.options,
- $el = this.element,
- dbtable_name;
+ if ( isFix ) {
+ $spliter.addClass( "ui-fixed" );
+ } else {
+ $spliter.removeClass( "ui-fixed" );
+ }
+ });
+ self._layout();
+ },
- t.destroy();
+ _dividerVertical : function ( isDividerVertical ) {
+ var self = this,
+ $el = self.element,
+ isHorizontal = isDividerVertical,
+ $panes = null,
+ $spliters = null,
+ $bar = null,
+ $handle = null;
- $.extend(this, {
- _itemData: function ( idx ) { return null; },
- _numItemData: 0,
- _cacheItemData: function ( minIdx, maxIdx ) { },
- _lastIndex: 0
- });
+ $panes = $el.children( ".ui-pane" );
+ $spliters = $el.children( ".ui-spliter" );
+ $bar = $spliters.children( ".ui-spliter-bar" );
+ $handle = $bar.children( ".ui-spliter-handle" );
+ $el.removeClass( "ui-direction-vertical" );
+ $el.removeClass( "ui-direction-horizontal" );
+ $el.addClass( "ui-splitview ui-direction-" + self._direction( isHorizontal ) );
- // create listview markup
- t.element.addClass( function ( i, orig ) {
- return orig + " ui-listview ui-extendable-list-container" + ( t.options.inset ? " ui-listview-inset ui-corner-all ui-shadow " : "" );
+ $panes.css( {
+ "left" : "",
+ "top" : "",
+ "width" : "",
+ "height" : ""
});
- o.id = "#" + $el.attr( "id" );
+ $spliters.css( {
+ "left" : "",
+ "top" : "",
+ "width" : "",
+ "height" : ""
+ });
- if ( $el.data( "extenditems" ) ) {
- o.extenditems = parseInt( $el.data( "extenditems" ), 10 );
- }
+ $bar.css( {
+ "width" : "",
+ "height" : ""
+ });
- $( o.id ).bind( "pagehide", function (e) {
- $( o.id ).empty();
+ $handle.css( {
+ "left" : "",
+ "top" : ""
});
- /* Scroll view */
- if ( $( ".ui-scrollview-clip" ).size() > 0) {
- o.scrollview = true;
- } else {
- o.scrollview = false;
+ if ( self._getContainerSize( $el[ 0 ].style.width, $el[ 0 ].style.height ) ) {
+ self._layout();
}
+ },
- if ( args ) {
- if ( !t._loadData( args ) ) {
- return;
- }
- } else {
- // Legacy support: dbtable
- console.warn("WARNING: The data interface of extendable list is changed. \nOld data interface(data-dbtable) is still supported, but will be removed in next version. \nPlease fix your code soon!");
+ _ratio : function ( ratioParam ) {
+ var self = this,
+ $el = self.element,
+ $panes = $el.children( ".ui-pane" ),
+ panesLength = $panes.length;
- if ( $( o.id ).hasClass( "elLoadSuccess" ) ) {
- dbtable_name = $el.jqmData('dbtable');
- o.dbtable = window[ dbtable_name ];
- if ( !(o.dbtable) ) {
- o.dbtable = { };
- }
- t._itemData = function ( idx ) {
- return o.dbtable[ idx ];
- };
- t._numItemData = o.dbtable.length;
+ self._convertRatio( ratioParam, panesLength );
+ self._layout();
+ },
- } else {
- console.warn("No elLoadSuccess class");
- return;
- }
- }
+ _refresh : function ( initRatio, fromFirstPane ) {
+ var self = this,
+ $el = self.element;
- if ( $el.data( "template" ) ) {
- o.template = $el.data( "template" );
+ initRatio = !!initRatio;
+ fromFirstPane = !!fromFirstPane;
- /* to support swipe list, <li> or <ul> can be main node of extendable list. */
- if ( $el.data( "swipelist" ) == true ) {
- o.childSelector = " ul";
- } else {
- o.shildSelector = " li";
- }
+ if ( self._getContainerSize( $el[ 0 ].style.width, $el[ 0 ].style.height ) ) {
+ self._layout( initRatio, fromFirstPane );
}
- t._initList( args );
},
- _loadData : function ( args ) {
- var self = this;
-
- if ( args.itemData && typeof args.itemData == 'function' ) {
- self._itemData = args.itemData;
- } else {
- return false;
- }
- if ( args.numItemData ) {
- if ( typeof args.numItemData == 'function' ) {
- self._numItemData = args.numItemData( );
- } else if ( typeof args.numItemData == 'number' ) {
- self._numItemData = args.numItemData;
- } else {
- return false;
- }
- } else {
- return false;
+ pane : function ( id, element ) {
+ if ( typeof id !== "string" ) {
+ return null;
}
- return true;
- },
+ var self = this,
+ $el = self.element,
+ $targetPane = $el.children( id ),
+ $targetView = null,
+ elementParent = null;
- destroy : function () {
- var o = this.options,
- eOTAL_ITEMS = 0,
- last_index = 0;
-
- $( o.id ).empty();
+ if ( !$targetPane.hasClass( "ui-pane" ) ) {
+ return null;
+ }
- $( "#load_more_message" ).die();
- },
+ // getter
+ if ( !element ) {
+ return $targetPane.contents();
+ }
- _itemApply: function ( $list, item ) {
- var $countli = item.find( ".ui-li-count" );
+ // setter
+ if ( $targetPane.hasClass( "ui-scrollview-clip" ) ) {
+ $targetPane.scrollview( "scrollTo", 0, 0, 0 );
- if ( $countli.length ) {
- item.addClass( "ui-li-has-count" );
+ $targetView = $targetPane.children( ".ui-scrollview-view" );
+ if ( !$targetView.length ) {
+ return null;
+ }
+ } else {
+ $targetView = $targetPane;
}
- $countli.addClass( "ui-btn-up-" + ( $list.jqmData( "counttheme" ) || this.options.countTheme ) + " ui-btn-corner-all" );
+ elementParent = element.parent();
+ if ( elementParent.length && elementParent[ 0 ] === $targetView[ 0 ] ) {
+ return;
+ }
- // TODO class has to be defined in markup
- item.find( "h1, h2, h3, h4, h5, h6" ).addClass( "ui-li-heading" ).end()
- .find( "p, dl" ).addClass( "ui-li-desc" ).end()
- .find( ">img:eq(0), .ui-link-inherit>img:eq(0)" ).addClass( "ui-li-thumb" ).each(function () {
- item.addClass( $( this ).is( ".ui-li-icon" ) ? "ui-li-has-icon" : "ui-li-has-thumb" );
- }).end()
- .find( ".ui-li-aside" ).each(function () {
- var $this = $( this );
- $this.prependTo( $this.parent() ); //shift aside to front for css float
- });
+ $targetView.empty().append( element ).trigger( "create" );
+ $targetView.fadeIn( 'fast' );
},
- _removeCorners: function ( li, which ) {
- var top = "ui-corner-top ui-corner-tr ui-corner-tl",
- bot = "ui-corner-bottom ui-corner-br ui-corner-bl";
-
- li = li.add( li.find( ".ui-btn-inner, .ui-li-link-alt, .ui-li-thumb" ) );
-
- if ( which === "top" ) {
- li.removeClass( top );
- } else if ( which === "bottom" ) {
- li.removeClass( bot );
- } else {
- li.removeClass( top + " " + bot );
+ maximize : function ( id ) {
+ if ( typeof id !== "string" ) {
+ return;
}
- },
- _refreshCorners: function ( create ) {
- var $li,
- $visibleli,
- $topli,
- $bottomli;
+ var self = this,
+ $el = self.element,
+ $panes = self.panes,
+ $targetPane = $el.children( id );
- if ( this.options.inset ) {
- $li = this.element.children( "li" );
- // at create time the li are not visible yet so we need to rely on .ui-screen-hidden
- $visibleli = create ? $li.not( ".ui-screen-hidden" ) : $li.filter( ":visible" );
+ if ( !$targetPane.hasClass( "ui-pane" ) ) {
+ return;
+ }
- this._removeCorners( $li );
+ self.savedRatio = self.options.ratio.slice();
- // Select the first visible li element
- $topli = $visibleli.first()
- .addClass( "ui-corner-top" );
+ self.options.ratio = [];
+ $panes.each( function ( i ) {
+ self.options.ratio.push( ( this === $targetPane[ 0 ] ) ? 1 : 0 );
+ });
- $topli.add( $topli.find( ".ui-btn-inner" ) )
- .find( ".ui-li-link-alt" )
- .addClass( "ui-corner-tr" )
- .end()
- .find( ".ui-li-thumb" )
- .not( ".ui-li-icon" )
- .addClass( "ui-corner-tl" );
+ self._layout();
+ },
- // Select the last visible li element
- $bottomli = $visibleli.last()
- .addClass( "ui-corner-bottom" );
+ restore : function () {
+ var self = this;
- $bottomli.add( $bottomli.find( ".ui-btn-inner" ) )
- .find( ".ui-li-link-alt" )
- .addClass( "ui-corner-br" )
- .end()
- .find( ".ui-li-thumb" )
- .not( ".ui-li-icon" )
- .addClass( "ui-corner-bl" );
+ if ( !self.savedRatio.length ) {
+ return;
}
- },
- refresh: function ( create ) {
- this.parentPage = this.element.closest( ".ui-page" );
- this._createSubPages();
+ self.options.ratio = self.savedRatio.slice();
+ self._adjustRatio( self.panes.length );
- var o = this.options,
- $list = this.element,
- self = this,
- dividertheme = $list.jqmData( "dividertheme" ) || o.dividerTheme,
- listsplittheme = $list.jqmData( "splittheme" ),
- listspliticon = $list.jqmData( "spliticon" ),
- li = $list.children( "li" ),
- counter = $.support.cssPseudoElement || !$.nodeName( $list[ 0 ], "ol" ) ? 0 : 1,
- item,
- itemClass,
- itemTheme,
- a,
- last,
- splittheme,
- countParent,
- icon,
- pos,
- numli;
+ self._layout();
+ }
+ });
- if ( counter ) {
- $list.find( ".ui-li-dec" ).remove();
- }
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $.tizen.splitview.prototype.enhanceWithin( e.target );
+ });
+} ( jQuery, window, document ) );
- for ( pos = 0, numli = li.length; pos < numli; pos++ ) {
- item = li.eq( pos );
- itemClass = "ui-li";
- // If we're creating the element, we update it regardless
- if ( create || !item.hasClass( "ui-li" ) ) {
- itemTheme = item.jqmData( "theme" ) || o.theme;
- a = item.children( "a" );
- if ( a.length ) {
- icon = item.jqmData( "icon" );
+/*
+ * set TIZEN specific configures
+ */
- item.buttonMarkup({
- wrapperEls: "div",
- shadow: false,
- corners: false,
- iconpos: "right",
- /* icon: a.length > 1 || icon === false ? false : icon || "arrow-r",*/
- icon: false, /* Remove unnecessary arrow icon */
- theme: itemTheme
- });
+( function( $, window, undefined ) {
- if ( ( icon != false ) && ( a.length == 1 ) ) {
- item.addClass( "ui-li-has-arrow" );
- }
+ /* set default transition */
+ $.mobile.defaultPageTransition = "none";
- a.first().addClass( "ui-link-inherit" );
+ /* depth transition */
+ $.mobile.transitionHandlers.depth = $.mobile.transitionHandlers.simultaneous;
+ $.mobile.transitionFallbacks.depth = "fade";
- if ( a.length > 1 ) {
- itemClass += " ui-li-has-alt";
+ /* Button data-corners default value */
+ $.fn.buttonMarkup.defaults.corners = false;
- last = a.last();
- splittheme = listsplittheme || last.jqmData( "theme" ) || o.splitTheme;
+ /* button hover delay */
+ $.mobile.buttonMarkup.hoverDelay = 0;
- last.appendTo(item)
- .attr( "title", last.getEncodedText() )
- .addClass( "ui-li-link-alt" )
- .empty()
- .buttonMarkup({
- shadow: false,
- corners: false,
- theme: itemTheme,
- icon: false,
- iconpos: false
- })
- .find( ".ui-btn-inner" )
- .append(
- $( "<span />" ).buttonMarkup( {
- shadow : true,
- corners : true,
- theme : splittheme,
- iconpos : "notext",
- icon : listspliticon || last.jqmData( "icon" ) || o.splitIcon
- })
- );
- }
- } else if ( item.jqmData( "role" ) === "list-divider" ) {
+})( jQuery, this );
- itemClass += " ui-li-divider ui-btn ui-bar-" + dividertheme;
- item.attr( "role", "heading" );
- //reset counter when a divider heading is encountered
- if ( counter ) {
- counter = 1;
- }
- } else {
- itemClass += " ui-li-static ui-body-" + itemTheme;
- }
- }
- if ( counter && itemClass.indexOf( "ui-li-divider" ) < 0 ) {
- countParent = item.is( ".ui-li-static:first" ) ? item : item.find( ".ui-link-inherit" );
+/****************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Author: Wongi Lee <wongi11.lee@samsung.com>
+*/
+
+/**
+ * Extendable List Widget for unlimited data.
+ * To support more then 1,000 items, special list widget developed.
+ * Fast initialize and append some element into the DOM tree repeatedly.
+ * DB connection and works like DB cursor.
+ *
+ * HTML Attributes:
+ *
+ * data-role: extendablelist
+ * data-template : jQuery.template ID that populate into extendable list. A button : a <DIV> element with "data-role : button" should be included on data-template.
+ * data-dbtable : DB Table name. It used as window[DB NAME]. Loaded data should be converted as window object.
+ * data-extenditems : Number of elements to extend at once.
+ *
+ * ID : <UL> element that has "data-role=extendablelist" must have ID attribute.
+ * Class : <UL> element that has "data-role=extendablelist" should have "vlLoadSuccess" class to guaranty DB loading is completed.
+ * tmp_load_more : Template ID for "load more" message and button.
+ *
+ *
+ *APIs:
+ * create ( {
+ * itemData: function ( idx ) { return json_obj; },
+ * numItemData: number or function () { return number; },
+ * cacheItemData: function ( minIdx, maxIdx ) {}
+ * } )
+ * : Create a extendable list widget. At this moment, _create method is called.
+ * args : A collection of options
+ * itemData: A function that returns JSON object for given index. Mandatory.
+ * numItemData: Total number of itemData. Mandatory.
+ * cacheItemData: Extendable list will ask itemData between minIdx and maxIdx.
+ * Developers can implement this function for preparing data.
+ * Optional.
+ *
+ *Examples:
+ *
+ * <script id="tmp-3-1-1" type="text/x-jquery-tmpl">
+ * <li class="ui-li-3-1-1"><span class="ui-li-text-main">${NAME}</span></li>
+ * </script>
+ *
+ * <script id="tmp_load_more" type="text/x-jquery-tmpl">
+ * <li class="ui-li-3-1-1" style="text-align:center; margin:0 auto">
+ * <div data-role="button">Load ${NUM_MORE_ITEMS} more items</div>
+ * </li>
+ * </script>
+ *
+ * <ul id = "extendable_list_main" data-role="extendablelist" data-extenditems="50" data-template="tmp-3-1-1">
+ * </ul>
+ *
+ */
+
+/**
+ @class Extendablelist
+ In the Web environment, it is challenging to display a large amount of data in a list, such as displaying a contact list of over 1000 list items. It takes time to display the entire list in HTML and the DOM manipulation is complex.
+ The extendable list widget is used to display a list of unlimited data elements on the screen for better performance. The list is extended if you click the button at the bottom of the list to load more data elements. Extendable lists are based on the jQuery.template plugin as described in the jQuery documentation for jQuery.template plugin.<br/>
+ To add a extendable list widget to the application, use the following code:
+
+ <script id="tmp-3-1-1" type="text/x-jquery-tmpl">
+ <li class="ui-li-3-1-1"><span class="ui-li-text-main">${NAME}</span></li>
+ </script>
+ <script id="tmp_load_more" type="text/x-jquery-tmpl">
+ <li class="ui-li-3-1-1" style="text-align:center; margin:0 auto">
+ <div data-role="button">Load ${NUM_MORE_ITEMS} more items</div>
+ </li>
+ </script>
+ <ul id="extendable_list_main" data-role="extendablelist" data-extenditems="50" data-template="tmp-3-1-1">
+ </ul>
+*/
+/**
+ @property {String} data-role
+ Creates the extendable list view. The value must be set to extendablelist. Only the <ul> element, which a id attribute defined, supports this option. Also, the elLoadSuccess class attribute must be defined in the <ul> element to ensure that loading data from the database is complete.
+*/
+/**
+ @property {String} data-template
+ Specifies the jQuery.template element ID. The jQuery.template must be defined. The template style can use rem units to support scalability. For using the button at the bottom of the list to load more data elements, there must be list view template with the button. The attribute ID must be tmp_load_more.
+*/
+/**
+ @property {Integer} data-extenditems
+ Defines the number of data elements to be extended at a time.
+*/
+( function ( $, undefined ) {
- countParent.addClass( "ui-li-jsnumbering" )
- .prepend( "<span class='ui-li-dec'>" + (counter++) + ". </span>" );
- }
+ //Keeps track of the number of lists per page UID
+ //This allows support for multiple nested list in the same page
+ //https://github.com/jquery/jquery-mobile/issues/1617
+ var listCountPerPage = {};
- item.add( item.children( ".ui-btn-inner" ) ).addClass( itemClass );
+ $.widget( "tizen.extendablelist", $.mobile.widget, {
+ options: {
+ theme: "s",
+ countTheme: "c",
+ headerTheme: "b",
+ dividerTheme: "b",
+ splitIcon: "arrow-r",
+ splitTheme: "b",
+ inset: false,
+ id: "", /* Extendable list UL elemet's ID */
+ extenditems: 50, /* Number of append items */
+ childSelector: " li", /* To support swipe list */
+ dbtable: "",
+ template : "", /* Template for each list item */
+ loadmore : "tmp_load_more", /* Template for "Load more" message */
+ scrollview: false,
+ initSelector: ":jqmData(role='extendablelist')"
+ },
- self._itemApply( $list, item );
- }
+ _stylerMouseUp: function () {
+ $( this ).addClass( "ui-btn-up-s" );
+ $( this ).removeClass( "ui-btn-down-s" );
+ },
- this._refreshCorners( create );
+ _stylerMouseDown: function () {
+ $( this ).addClass( "ui-btn-down-s" );
+ $( this ).removeClass( "ui-btn-up-s" );
},
- //create a string for ID/subpage url creation
- _idStringEscape: function ( str ) {
- return str.replace(/\W/g , "-");
+ _stylerMouseOver: function () {
+ $( this ).toggleClass( "ui-btn-hover-s" );
+ },
+ _stylerMouseOut: function () {
+ $( this ).toggleClass( "ui-btn-hover-s" );
+ $( this ).addClass( "ui-btn-up-s" );
+ $( this ).removeClass( "ui-btn-down-s" );
},
- _createSubPages: function () {
- var parentList = this.element,
- parentPage = parentList.closest( ".ui-page" ),
- parentUrl = parentPage.jqmData( "url" ),
- parentId = parentUrl || parentPage[ 0 ][ $.expando ],
- parentListId = parentList.attr( "id" ),
- o = this.options,
- dns = "data-" + $.mobile.ns,
- self = this,
- persistentFooterID = parentPage.find( ":jqmData(role='footer')" ).jqmData( "id" ),
- hasSubPages,
- newRemove;
+ _pushData: function ( template ) {
+ var o = this.options,
+ t = this,
+ i = 0,
+ myTemplate = $( "#" + template ),
+ loadMoreItems = ( o.extenditems > t._numItemData - t._lastIndex ? t._numItemData - t.lastIndex : o.extenditems ),
+ htmlData;
- if ( typeof listCountPerPage[ parentId ] === "undefined" ) {
- listCountPerPage[ parentId ] = -1;
- }
+ for (i = 0; i < loadMoreItems; i++ ) {
+ htmlData = myTemplate.tmpl( t._itemData( i ) );
+ $( o.id ).append( $( htmlData ).attr( 'id', 'li_' + i ) );
- parentListId = parentListId || ++listCountPerPage[ parentId ];
+ /* Add style */
+ $( o.id + ">" + o.childSelector )
+ .addClass( "ui-btn-up-s" )
+ .bind( "mouseup", t._stylerMouseUp )
+ .bind( "mousedown", t._stylerMouseDown )
+ .bind( "mouseover", t._stylerMouseOver )
+ .bind( "mouseout", t._stylerMouseOut );
- $( parentList.find( "li>ul, li>ol" ).toArray().reverse() ).each(function ( i ) {
- var self = this,
- list = $( this ),
- listId = list.attr( "id" ) || parentListId + "-" + i,
- parent = list.parent(),
- nodeEls,
- title = nodeEls.first().getEncodedText(),//url limits to first 30 chars of text
- id = ( parentUrl || "" ) + "&" + $.mobile.subPageUrlKey + "=" + listId,
- theme = list.jqmData( "theme" ) || o.theme,
- countTheme = list.jqmData( "counttheme" ) || parentList.jqmData( "counttheme" ) || o.countTheme,
- newPage,
- anchor;
+ t._lastIndex += 1;
+ }
- nodeEls = $( list.prevAll().toArray().reverse() );
- nodeEls = nodeEls.length ? nodeEls : $( "<span>" + $.trim(parent.contents()[ 0 ].nodeValue) + "</span>" );
+ /* After push data, re-style extendable list widget */
+ $( o.id ).trigger( "create" );
+ },
- //define hasSubPages for use in later removal
- hasSubPages = true;
+ _loadmore: function ( event ) {
+ var t = event.data, // <li> element
+ o = t.options,
+ i = 0,
+ myTemplate = $( "#" + o.template ),
+ loadMoreItems = ( o.extenditems > t._numItemData - t._lastIndex ? t._numItemData - t._lastIndex : o.extenditems ),
+ htmlData,
+ more_items_to_load,
+ num_next_load_items;
- newPage = list.detach()
- .wrap( "<div " + dns + "role='page' " + dns + "url='" + id + "' " + dns + "theme='" + theme + "' " + dns + "count-theme='" + countTheme + "'><div " + dns + "role='content'></div></div>" )
- .parent()
- .before( "<div " + dns + "role='header' " + dns + "theme='" + o.headerTheme + "'><div class='ui-title'>" + title + "</div></div>" )
- .after( persistentFooterID ? $( "<div " + dns + "role='footer' " + dns + "id='" + persistentFooterID + "'>" ) : "" )
- .parent()
- .appendTo( $.mobile.pageContainer );
+ /* Remove load more message */
+ $( "#load_more_message" ).remove();
- newPage.page();
+ /* Append More Items */
+ for ( i = 0; i < loadMoreItems; i++ ) {
+ htmlData = myTemplate.tmpl( t._itemData( t._lastIndex ) );
+ $( o.id ).append( $( htmlData ).attr( 'id', 'li_' + t._lastIndex ) );
+ t._lastIndex += 1;
+ }
- anchor = parent.find('a:first');
+ /* Append "Load more" message on the last of list */
+ if ( t._numItemData > t._lastIndex ) {
+ myTemplate = $( "#" + o.loadmore );
+ more_items_to_load = t._numItemData - t._lastIndex;
+ num_next_load_items = ( o.extenditems <= more_items_to_load ) ? o.extenditems : more_items_to_load;
+ htmlData = myTemplate.tmpl( { NUM_MORE_ITEMS : num_next_load_items } );
+ // Button minimum height(37px)
+ $( o.id ).append( $( htmlData ).attr( 'id', "load_more_message" ).css( 'min-height' , "37px") );
+ }
- if ( !anchor.length ) {
- anchor = $( "<a/>" ).html( nodeEls || title ).prependTo( parent.empty() );
- }
+ $( o.id ).trigger( "create" );
+ $( o.id ).extendablelist( "refresh" );
+ },
- anchor.attr( "href", "#" + id );
+ recreate: function ( newArray ) {
+ this._create( {
+ itemData: function ( idx ) { return newArray[ idx ]; },
+ numItemData: newArray.length
+ } );
+ },
- }).extendablelist();
+ _initList: function (args ) {
+ var t = this,
+ o = this.options,
+ myTemplate,
+ more_items_to_load,
+ num_next_load_items,
+ htmlData;
- // on pagehide, remove any nested pages along with the parent page, as long as they aren't active
- // and aren't embedded
- if ( hasSubPages &&
- parentPage.is( ":jqmData(external-page='true')" ) &&
- parentPage.data( "page" ).options.domCache === false ) {
+ /* Make Gen list by template */
+ if ( t._lastIndex <= 0 ) {
+ t._pushData( o.template );
- newRemove = function ( e, ui ) {
- var nextPage = ui.nextPage, npURL;
+ /* Append "Load more" message on the last of list */
+ if ( t._numItemData > t._lastIndex ) {
+ myTemplate = $( "#" + o.loadmore );
+ more_items_to_load = t._numItemData - t._lastIndex;
+ num_next_load_items = ( o.extenditems <= more_items_to_load) ? o.extenditems : more_items_to_load;
+ htmlData = myTemplate.tmpl( { NUM_MORE_ITEMS : num_next_load_items } );
+ // Button minimum height(37px)
+ $( o.id ).append( $( htmlData ).attr( 'id', "load_more_message" ).css( 'min-height' , "37px") );
- if ( ui.nextPage ) {
- npURL = nextPage.jqmData( "url" );
- if ( npURL.indexOf( parentUrl + "&" + $.mobile.subPageUrlKey ) !== 0 ) {
- self.childPages().remove();
- parentPage.remove();
- }
- }
- };
+ $( "#load_more_message" ).live( "click", t, t._loadmore );
+ } else {
+ /* No more items to load */
+ $( "#load_more_message" ).die();
+ $( "#load_more_message" ).remove();
+ }
+ }
- // unbind the original page remove and replace with our specialized version
- parentPage
- .unbind( "pagehide.remove" )
- .bind( "pagehide.remove", newRemove);
+ if ( o.childSelector == " ul" ) {
+ $( o.id + " ul" ).swipelist();
}
- },
- // TODO sort out a better way to track sub pages of the extendable listview this is brittle
- childPages: function () {
- var parentUrl = this.parentPage.jqmData( "url" );
+ $( o.id ).trigger( "create" );
- return $( ":jqmData(url^='" + parentUrl + "&" + $.mobile.subPageUrlKey + "')" );
- }
- });
+ t.refresh( true );
+ },
- //auto self-init widgets
- $( document ).bind( "pagecreate create", function ( e ) {
- $( $.tizen.extendablelist.prototype.options.initSelector, e.target ).extendablelist();
- });
+ create: function () {
+ var o = this.options;
-}( jQuery ));
+ /* external API for AJAX callback */
+ this._create.apply( this, arguments );
+ },
+ _create: function ( args ) {
+ var t = this,
+ o = this.options,
+ $el = this.element,
+ dbtable_name;
-ensureNS("jQuery.mobile.tizen.clrlib");
+ t.destroy();
-jQuery.extend( jQuery.mobile.tizen.clrlib,
-{
- nearestInt: function(val) {
- var theFloor = Math.floor(val);
+ $.extend(this, {
+ _itemData: function ( idx ) { return null; },
+ _numItemData: 0,
+ _cacheItemData: function ( minIdx, maxIdx ) { },
+ _lastIndex: 0
+ });
- return (((val - theFloor) > 0.5) ? (theFloor + 1) : theFloor);
- },
- /*
- * Converts html color string to rgb array.
- *
- * Input: string clr_str, where
- * clr_str is of the form "#aabbcc"
- *
- * Returns: [ r, g, b ], where
- * r is in [0, 1]
- * g is in [0, 1]
- * b is in [0, 1]
- */
- HTMLToRGB: function(clr_str) {
- clr_str = (('#' == clr_str.charAt(0)) ? clr_str.substring(1) : clr_str);
+ // create listview markup
+ t.element.addClass( function ( i, orig ) {
+ return orig + " ui-listview ui-extendable-list-container" + ( t.options.inset ? " ui-listview-inset ui-corner-all ui-shadow " : "" );
+ });
- return ([
- clr_str.substring(0, 2),
- clr_str.substring(2, 4),
- clr_str.substring(4, 6)
- ].map(function(val) {
- return parseInt(val, 16) / 255.0;
- }));
- },
+ o.id = "#" + $el.attr( "id" );
- /*
- * Converts rgb array to html color string.
- *
- * Input: [ r, g, b ], where
- * r is in [0, 1]
- * g is in [0, 1]
- * b is in [0, 1]
- *
- * Returns: string of the form "#aabbcc"
- */
- RGBToHTML: function(rgb) {
- return ("#" +
- rgb.map(function(val) {
- var ret = val * 255,
- theFloor = Math.floor(ret);
+ if ( $el.data( "extenditems" ) ) {
+ o.extenditems = parseInt( $el.data( "extenditems" ), 10 );
+ }
- ret = ((ret - theFloor > 0.5) ? (theFloor + 1) : theFloor);
- ret = (((ret < 16) ? "0" : "") + (ret & 0xff).toString(16));
- return ret;
- })
- .join(""));
- },
+ $( o.id ).bind( "pagehide", function (e) {
+ $( o.id ).empty();
+ });
- /*
- * Converts hsl to rgb.
- *
- * From http://130.113.54.154/~monger/hsl-rgb.html
- *
- * Input: [ h, s, l ], where
- * h is in [0, 360]
- * s is in [0, 1]
- * l is in [0, 1]
- *
- * Returns: [ r, g, b ], where
- * r is in [0, 1]
- * g is in [0, 1]
- * b is in [0, 1]
- */
- HSLToRGB: function(hsl) {
- var h = hsl[0] / 360.0, s = hsl[1], l = hsl[2];
+ /* Scroll view */
+ if ( $( ".ui-scrollview-clip" ).size() > 0) {
+ o.scrollview = true;
+ } else {
+ o.scrollview = false;
+ }
- if (0 === s)
- return [ l, l, l ];
+ if ( args ) {
+ if ( !t._loadData( args ) ) {
+ return;
+ }
+ } else {
+ // Legacy support: dbtable
+ console.warn("WARNING: The data interface of extendable list is changed. \nOld data interface(data-dbtable) is still supported, but will be removed in next version. \nPlease fix your code soon!");
- var temp2 = ((l < 0.5)
- ? l * (1.0 + s)
- : l + s - l * s),
- temp1 = 2.0 * l - temp2,
- temp3 = {
- r: h + 1.0 / 3.0,
- g: h,
- b: h - 1.0 / 3.0
- };
+ if ( $( o.id ).hasClass( "elLoadSuccess" ) ) {
+ dbtable_name = $el.jqmData('dbtable');
+ o.dbtable = window[ dbtable_name ];
+ if ( !(o.dbtable) ) {
+ o.dbtable = { };
+ }
+ t._itemData = function ( idx ) {
+ return o.dbtable[ idx ];
+ };
+ t._numItemData = o.dbtable.length;
- temp3.r = ((temp3.r < 0) ? (temp3.r + 1.0) : ((temp3.r > 1) ? (temp3.r - 1.0) : temp3.r));
- temp3.g = ((temp3.g < 0) ? (temp3.g + 1.0) : ((temp3.g > 1) ? (temp3.g - 1.0) : temp3.g));
- temp3.b = ((temp3.b < 0) ? (temp3.b + 1.0) : ((temp3.b > 1) ? (temp3.b - 1.0) : temp3.b));
+ } else {
+ console.warn("No elLoadSuccess class");
+ return;
+ }
+ }
- ret = [
- (((6.0 * temp3.r) < 1) ? (temp1 + (temp2 - temp1) * 6.0 * temp3.r) :
- (((2.0 * temp3.r) < 1) ? temp2 :
- (((3.0 * temp3.r) < 2) ? (temp1 + (temp2 - temp1) * ((2.0 / 3.0) - temp3.r) * 6.0) :
- temp1))),
- (((6.0 * temp3.g) < 1) ? (temp1 + (temp2 - temp1) * 6.0 * temp3.g) :
- (((2.0 * temp3.g) < 1) ? temp2 :
- (((3.0 * temp3.g) < 2) ? (temp1 + (temp2 - temp1) * ((2.0 / 3.0) - temp3.g) * 6.0) :
- temp1))),
- (((6.0 * temp3.b) < 1) ? (temp1 + (temp2 - temp1) * 6.0 * temp3.b) :
- (((2.0 * temp3.b) < 1) ? temp2 :
- (((3.0 * temp3.b) < 2) ? (temp1 + (temp2 - temp1) * ((2.0 / 3.0) - temp3.b) * 6.0) :
- temp1)))];
+ if ( $el.data( "template" ) ) {
+ o.template = $el.data( "template" );
- return ret;
- },
+ /* to support swipe list, <li> or <ul> can be main node of extendable list. */
+ if ( $el.data( "swipelist" ) == true ) {
+ o.childSelector = " ul";
+ } else {
+ o.shildSelector = " li";
+ }
+ }
+ t._initList( args );
+ },
- /*
- * Converts hsv to rgb.
- *
- * Input: [ h, s, v ], where
- * h is in [0, 360]
- * s is in [0, 1]
- * v is in [0, 1]
- *
- * Returns: [ r, g, b ], where
- * r is in [0, 1]
- * g is in [0, 1]
- * b is in [0, 1]
- */
- HSVToRGB: function(hsv) {
- return $.mobile.tizen.clrlib.HSLToRGB($.mobile.tizen.clrlib.HSVToHSL(hsv));
- },
+ _loadData : function ( args ) {
+ var self = this;
- /*
- * Converts rgb to hsv.
- *
- * from http://coecsl.ece.illinois.edu/ge423/spring05/group8/FinalProject/HSV_writeup.pdf
- *
- * Input: [ r, g, b ], where
- * r is in [0, 1]
- * g is in [0, 1]
- * b is in [0, 1]
- *
- * Returns: [ h, s, v ], where
- * h is in [0, 360]
- * s is in [0, 1]
- * v is in [0, 1]
- */
- RGBToHSV: function(rgb) {
- var min, max, delta, h, s, v, r = rgb[0], g = rgb[1], b = rgb[2];
+ if ( args.itemData && typeof args.itemData == 'function' ) {
+ self._itemData = args.itemData;
+ } else {
+ return false;
+ }
+ if ( args.numItemData ) {
+ if ( typeof args.numItemData == 'function' ) {
+ self._numItemData = args.numItemData( );
+ } else if ( typeof args.numItemData == 'number' ) {
+ self._numItemData = args.numItemData;
+ } else {
+ return false;
+ }
+ } else {
+ return false;
+ }
+ return true;
+ },
- min = Math.min(r, Math.min(g, b));
- max = Math.max(r, Math.max(g, b));
- delta = max - min;
- h = 0;
- s = 0;
- v = max;
+ destroy : function () {
+ var o = this.options,
+ eOTAL_ITEMS = 0,
+ last_index = 0;
- if (delta > 0.00001) {
- s = delta / max;
+ $( o.id ).empty();
- if (r === max)
- h = (g - b) / delta ;
- else
- if (g === max)
- h = 2 + (b - r) / delta ;
- else
- h = 4 + (r - g) / delta ;
+ $( "#load_more_message" ).die();
+ },
- h *= 60 ;
+ _itemApply: function ( $list, item ) {
+ var $countli = item.find( ".ui-li-count" );
- if (h < 0)
- h += 360 ;
- }
+ if ( $countli.length ) {
+ item.addClass( "ui-li-has-count" );
+ }
- return [h, s, v];
- },
+ $countli.addClass( "ui-btn-up-" + ( $list.jqmData( "counttheme" ) || this.options.countTheme ) + " ui-btn-corner-all" );
- /*
- * Converts hsv to hsl.
- *
- * Input: [ h, s, v ], where
- * h is in [0, 360]
- * s is in [0, 1]
- * v is in [0, 1]
- *
- * Returns: [ h, s, l ], where
- * h is in [0, 360]
- * s is in [0, 1]
- * l is in [0, 1]
- */
- HSVToHSL: function(hsv) {
- var max = hsv[2],
- delta = hsv[1] * max,
- min = max - delta,
- sum = max + min,
- half_sum = sum / 2,
- s_divisor = ((half_sum < 0.5) ? sum : (2 - max - min));
+ // TODO class has to be defined in markup
+ item.find( "h1, h2, h3, h4, h5, h6" ).addClass( "ui-li-heading" ).end()
+ .find( "p, dl" ).addClass( "ui-li-desc" ).end()
+ .find( ">img:eq(0), .ui-link-inherit>img:eq(0)" ).addClass( "ui-li-thumb" ).each(function () {
+ item.addClass( $( this ).is( ".ui-li-icon" ) ? "ui-li-has-icon" : "ui-li-has-thumb" );
+ }).end()
+ .find( ".ui-li-aside" ).each(function () {
+ var $this = $( this );
+ $this.prependTo( $this.parent() ); //shift aside to front for css float
+ });
+ },
- return [ hsv[0], ((0 == s_divisor) ? 0 : (delta / s_divisor)), half_sum ];
- },
+ _removeCorners: function ( li, which ) {
+ var top = "ui-corner-top ui-corner-tr ui-corner-tl",
+ bot = "ui-corner-bottom ui-corner-br ui-corner-bl";
+
+ li = li.add( li.find( ".ui-btn-inner, .ui-li-link-alt, .ui-li-thumb" ) );
+
+ if ( which === "top" ) {
+ li.removeClass( top );
+ } else if ( which === "bottom" ) {
+ li.removeClass( bot );
+ } else {
+ li.removeClass( top + " " + bot );
+ }
+ },
- /*
- * Converts rgb to hsl
- *
- * Input: [ r, g, b ], where
- * r is in [0, 1]
- * g is in [0, 1]
- * b is in [0, 1]
- *
- * Returns: [ h, s, l ], where
- * h is in [0, 360]
- * s is in [0, 1]
- * l is in [0, 1]
- */
- RGBToHSL: function(rgb) {
- return $.mobile.tizen.clrlib.HSVToHSL($.mobile.tizen.clrlib.RGBToHSV(rgb));
- }
-});
+ _refreshCorners: function ( create ) {
+ var $li,
+ $visibleli,
+ $topli,
+ $bottomli;
+ if ( this.options.inset ) {
+ $li = this.element.children( "li" );
+ // at create time the li are not visible yet so we need to rely on .ui-screen-hidden
+ $visibleli = create ? $li.not( ".ui-screen-hidden" ) : $li.filter( ":visible" );
+ this._removeCorners( $li );
-/*
- * set TIZEN specific configures
- */
+ // Select the first visible li element
+ $topli = $visibleli.first()
+ .addClass( "ui-corner-top" );
-( function( $, window, undefined ) {
+ $topli.add( $topli.find( ".ui-btn-inner" ) )
+ .find( ".ui-li-link-alt" )
+ .addClass( "ui-corner-tr" )
+ .end()
+ .find( ".ui-li-thumb" )
+ .not( ".ui-li-icon" )
+ .addClass( "ui-corner-tl" );
- /* set default transition */
- $.mobile.defaultPageTransition = "none";
+ // Select the last visible li element
+ $bottomli = $visibleli.last()
+ .addClass( "ui-corner-bottom" );
- /* depth transition */
- $.mobile.transitionHandlers.depth = $.mobile.transitionHandlers.simultaneous;
- $.mobile.transitionFallbacks.depth = "fade";
+ $bottomli.add( $bottomli.find( ".ui-btn-inner" ) )
+ .find( ".ui-li-link-alt" )
+ .addClass( "ui-corner-br" )
+ .end()
+ .find( ".ui-li-thumb" )
+ .not( ".ui-li-icon" )
+ .addClass( "ui-corner-bl" );
+ }
+ },
- /* Button data-corners default value */
- $.fn.buttonMarkup.defaults.corners = false;
+ refresh: function ( create ) {
+ this.parentPage = this.element.closest( ".ui-page" );
+ this._createSubPages();
- /* button hover delay */
- $.mobile.buttonMarkup.hoverDelay = 0;
+ var o = this.options,
+ $list = this.element,
+ self = this,
+ dividertheme = $list.jqmData( "dividertheme" ) || o.dividerTheme,
+ listsplittheme = $list.jqmData( "splittheme" ),
+ listspliticon = $list.jqmData( "spliticon" ),
+ li = $list.children( "li" ),
+ counter = $.support.cssPseudoElement || !$.nodeName( $list[ 0 ], "ol" ) ? 0 : 1,
+ item,
+ itemClass,
+ itemTheme,
+ a,
+ last,
+ splittheme,
+ countParent,
+ icon,
+ pos,
+ numli;
-})( jQuery, this );
+ if ( counter ) {
+ $list.find( ".ui-li-dec" ).remove();
+ }
+ for ( pos = 0, numli = li.length; pos < numli; pos++ ) {
+ item = li.eq( pos );
+ itemClass = "ui-li";
+ // If we're creating the element, we update it regardless
+ if ( create || !item.hasClass( "ui-li" ) ) {
+ itemTheme = item.jqmData( "theme" ) || o.theme;
+ a = item.children( "a" );
+ if ( a.length ) {
+ icon = item.jqmData( "icon" );
+ item.buttonMarkup({
+ wrapperEls: "div",
+ shadow: false,
+ corners: false,
+ iconpos: "right",
+ /* icon: a.length > 1 || icon === false ? false : icon || "arrow-r",*/
+ icon: false, /* Remove unnecessary arrow icon */
+ theme: itemTheme
+ });
-/* ***************************************************************************
- Flora License
+ if ( ( icon != false ) && ( a.length == 1 ) ) {
+ item.addClass( "ui-li-has-arrow" );
+ }
- Version 1.0, April, 2013
+ a.first().addClass( "ui-link-inherit" );
- http://floralicense.org/license/
+ if ( a.length > 1 ) {
+ itemClass += " ui-li-has-alt";
- TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+ last = a.last();
+ splittheme = listsplittheme || last.jqmData( "theme" ) || o.splitTheme;
- 1. Definitions.
+ last.appendTo(item)
+ .attr( "title", last.getEncodedText() )
+ .addClass( "ui-li-link-alt" )
+ .empty()
+ .buttonMarkup({
+ shadow: false,
+ corners: false,
+ theme: itemTheme,
+ icon: false,
+ iconpos: false
+ })
+ .find( ".ui-btn-inner" )
+ .append(
+ $( "<span />" ).buttonMarkup( {
+ shadow : true,
+ corners : true,
+ theme : splittheme,
+ iconpos : "notext",
+ icon : listspliticon || last.jqmData( "icon" ) || o.splitIcon
+ })
+ );
+ }
+ } else if ( item.jqmData( "role" ) === "list-divider" ) {
- "License" shall mean the terms and conditions for use, reproduction,
- and distribution as defined by Sections 1 through 9 of this document.
+ itemClass += " ui-li-divider ui-btn ui-bar-" + dividertheme;
+ item.attr( "role", "heading" );
- "Licensor" shall mean the copyright owner or entity authorized by
- the copyright owner that is granting the License.
+ //reset counter when a divider heading is encountered
+ if ( counter ) {
+ counter = 1;
+ }
- "Legal Entity" shall mean the union of the acting entity and
- all other entities that control, are controlled by, or are
- under common control with that entity. For the purposes of
- this definition, "control" means (i) the power, direct or indirect,
- to cause the direction or management of such entity,
- whether by contract or otherwise, or (ii) ownership of fifty percent (50%)
- or more of the outstanding shares, or (iii) beneficial ownership of
- such entity.
+ } else {
+ itemClass += " ui-li-static ui-body-" + itemTheme;
+ }
+ }
- "You" (or "Your") shall mean an individual or Legal Entity
- exercising permissions granted by this License.
+ if ( counter && itemClass.indexOf( "ui-li-divider" ) < 0 ) {
+ countParent = item.is( ".ui-li-static:first" ) ? item : item.find( ".ui-link-inherit" );
- "Source" form shall mean the preferred form for making modifications,
- including but not limited to software source code, documentation source,
- and configuration files.
+ countParent.addClass( "ui-li-jsnumbering" )
+ .prepend( "<span class='ui-li-dec'>" + (counter++) + ". </span>" );
+ }
- "Object" form shall mean any form resulting from mechanical
- transformation or translation of a Source form, including but
- not limited to compiled object code, generated documentation,
- and conversions to other media types.
+ item.add( item.children( ".ui-btn-inner" ) ).addClass( itemClass );
- "Work" shall mean the work of authorship, whether in Source or Object form,
- made available under the License, as indicated by a copyright notice
- that is included in or attached to the work (an example is provided
- in the Appendix below).
+ self._itemApply( $list, item );
+ }
- "Derivative Works" shall mean any work, whether in Source or Object form,
- that is based on (or derived from) the Work and for which the editorial
- revisions, annotations, elaborations, or other modifications represent,
- as a whole, an original work of authorship. For the purposes of this License,
- Derivative Works shall not include works that remain separable from,
- or merely link (or bind by name) to the interfaces of, the Work and
- Derivative Works thereof.
+ this._refreshCorners( create );
+ },
- "Contribution" shall mean any work of authorship, including the original
- version of the Work and any modifications or additions to that Work or
- Derivative Works thereof, that is intentionally submitted to Licensor
- for inclusion in the Work by the copyright owner or by an individual or
- Legal Entity authorized to submit on behalf of the copyright owner.
- For the purposes of this definition, "submitted" means any form of
- electronic, verbal, or written communication sent to the Licensor or
- its representatives, including but not limited to communication on
- electronic mailing lists, source code control systems, and issue
- tracking systems that are managed by, or on behalf of, the Licensor
- for the purpose of discussing and improving the Work, but excluding
- communication that is conspicuously marked or otherwise designated
- in writing by the copyright owner as "Not a Contribution."
+ //create a string for ID/subpage url creation
+ _idStringEscape: function ( str ) {
+ return str.replace(/\W/g , "-");
- "Contributor" shall mean Licensor and any individual or Legal Entity
- on behalf of whom a Contribution has been received by Licensor and
- subsequently incorporated within the Work.
+ },
- "Tizen Certified Platform" shall mean a software platform that complies
- with the standards set forth in the Tizen Compliance Specification
- and passes the Tizen Compliance Tests as defined from time to time
- by the Tizen Technical Steering Group and certified by the Tizen
- Association or its designated agent.
+ _createSubPages: function () {
+ var parentList = this.element,
+ parentPage = parentList.closest( ".ui-page" ),
+ parentUrl = parentPage.jqmData( "url" ),
+ parentId = parentUrl || parentPage[ 0 ][ $.expando ],
+ parentListId = parentList.attr( "id" ),
+ o = this.options,
+ dns = "data-" + $.mobile.ns,
+ self = this,
+ persistentFooterID = parentPage.find( ":jqmData(role='footer')" ).jqmData( "id" ),
+ hasSubPages,
+ newRemove;
- 2. Grant of Copyright License. Subject to the terms and conditions of
- this License, each Contributor hereby grants to You a perpetual,
- worldwide, non-exclusive, no-charge, royalty-free, irrevocable
- copyright license to reproduce, prepare Derivative Works of,
- publicly display, publicly perform, sublicense, and distribute the
- Work and such Derivative Works in Source or Object form.
+ if ( typeof listCountPerPage[ parentId ] === "undefined" ) {
+ listCountPerPage[ parentId ] = -1;
+ }
- 3. Grant of Patent License. Subject to the terms and conditions of
- this License, each Contributor hereby grants to You a perpetual,
- worldwide, non-exclusive, no-charge, royalty-free, irrevocable
- (except as stated in this section) patent license to make, have made,
- use, offer to sell, sell, import, and otherwise transfer the Work
- solely as incorporated into a Tizen Certified Platform, where such
- license applies only to those patent claims licensable by such
- Contributor that are necessarily infringed by their Contribution(s)
- alone or by combination of their Contribution(s) with the Work solely
- as incorporated into a Tizen Certified Platform to which such
- Contribution(s) was submitted. If You institute patent litigation
- against any entity (including a cross-claim or counterclaim
- in a lawsuit) alleging that the Work or a Contribution incorporated
- within the Work constitutes direct or contributory patent infringement,
- then any patent licenses granted to You under this License for that
- Work shall terminate as of the date such litigation is filed.
+ parentListId = parentListId || ++listCountPerPage[ parentId ];
- 4. Redistribution. You may reproduce and distribute copies of the
- Work or Derivative Works thereof pursuant to the copyright license
- above, in any medium, with or without modifications, and in Source or
- Object form, provided that You meet the following conditions:
+ $( parentList.find( "li>ul, li>ol" ).toArray().reverse() ).each(function ( i ) {
+ var self = this,
+ list = $( this ),
+ listId = list.attr( "id" ) || parentListId + "-" + i,
+ parent = list.parent(),
+ nodeEls,
+ title = nodeEls.first().getEncodedText(),//url limits to first 30 chars of text
+ id = ( parentUrl || "" ) + "&" + $.mobile.subPageUrlKey + "=" + listId,
+ theme = list.jqmData( "theme" ) || o.theme,
+ countTheme = list.jqmData( "counttheme" ) || parentList.jqmData( "counttheme" ) || o.countTheme,
+ newPage,
+ anchor;
- 1. You must give any other recipients of the Work or Derivative Works
- a copy of this License; and
- 2. You must cause any modified files to carry prominent notices stating
- that You changed the files; and
- 3. You must retain, in the Source form of any Derivative Works that
- You distribute, all copyright, patent, trademark, and attribution
- notices from the Source form of the Work, excluding those notices
- that do not pertain to any part of the Derivative Works; and
- 4. If the Work includes a "NOTICE" text file as part of its distribution,
- then any Derivative Works that You distribute must include a readable
- copy of the attribution notices contained within such NOTICE file,
- excluding those notices that do not pertain to any part of
- the Derivative Works, in at least one of the following places:
- within a NOTICE text file distributed as part of the Derivative Works;
- within the Source form or documentation, if provided along with the
- Derivative Works; or, within a display generated by the Derivative Works,
- if and wherever such third-party notices normally appear.
- The contents of the NOTICE file are for informational purposes only
- and do not modify the License.
+ nodeEls = $( list.prevAll().toArray().reverse() );
+ nodeEls = nodeEls.length ? nodeEls : $( "<span>" + $.trim(parent.contents()[ 0 ].nodeValue) + "</span>" );
- You may add Your own attribution notices within Derivative Works
- that You distribute, alongside or as an addendum to the NOTICE text
- from the Work, provided that such additional attribution notices
- cannot be construed as modifying the License. You may add Your own
- copyright statement to Your modifications and may provide additional or
- different license terms and conditions for use, reproduction, or
- distribution of Your modifications, or for any such Derivative Works
- as a whole, provided Your use, reproduction, and distribution of
- the Work otherwise complies with the conditions stated in this License.
+ //define hasSubPages for use in later removal
+ hasSubPages = true;
- 5. Submission of Contributions. Unless You explicitly state otherwise,
- any Contribution intentionally submitted for inclusion in the Work
- by You to the Licensor shall be under the terms and conditions of
- this License, without any additional terms or conditions.
- Notwithstanding the above, nothing herein shall supersede or modify
- the terms of any separate license agreement you may have executed
- with Licensor regarding such Contributions.
+ newPage = list.detach()
+ .wrap( "<div " + dns + "role='page' " + dns + "url='" + id + "' " + dns + "theme='" + theme + "' " + dns + "count-theme='" + countTheme + "'><div " + dns + "role='content'></div></div>" )
+ .parent()
+ .before( "<div " + dns + "role='header' " + dns + "theme='" + o.headerTheme + "'><div class='ui-title'>" + title + "</div></div>" )
+ .after( persistentFooterID ? $( "<div " + dns + "role='footer' " + dns + "id='" + persistentFooterID + "'>" ) : "" )
+ .parent()
+ .appendTo( $.mobile.pageContainer );
- 6. Trademarks. This License does not grant permission to use the trade
- names, trademarks, service marks, or product names of the Licensor,
- except as required for reasonable and customary use in describing the
- origin of the Work and reproducing the content of the NOTICE file.
+ newPage.page();
- 7. Disclaimer of Warranty. Unless required by applicable law or
- agreed to in writing, Licensor provides the Work (and each
- Contributor provides its Contributions) on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
- implied, including, without limitation, any warranties or conditions
- of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
- PARTICULAR PURPOSE. You are solely responsible for determining the
- appropriateness of using or redistributing the Work and assume any
- risks associated with Your exercise of permissions under this License.
+ anchor = parent.find('a:first');
- 8. Limitation of Liability. In no event and under no legal theory,
- whether in tort (including negligence), contract, or otherwise,
- unless required by applicable law (such as deliberate and grossly
- negligent acts) or agreed to in writing, shall any Contributor be
- liable to You for damages, including any direct, indirect, special,
- incidental, or consequential damages of any character arising as a
- result of this License or out of the use or inability to use the
- Work (including but not limited to damages for loss of goodwill,
- work stoppage, computer failure or malfunction, or any and all
- other commercial damages or losses), even if such Contributor
- has been advised of the possibility of such damages.
+ if ( !anchor.length ) {
+ anchor = $( "<a/>" ).html( nodeEls || title ).prependTo( parent.empty() );
+ }
- 9. Accepting Warranty or Additional Liability. While redistributing
- the Work or Derivative Works thereof, You may choose to offer,
- and charge a fee for, acceptance of support, warranty, indemnity,
- or other liability obligations and/or rights consistent with this
- License. However, in accepting such obligations, You may act only
- on Your own behalf and on Your sole responsibility, not on behalf
- of any other Contributor, and only if You agree to indemnify,
- defend, and hold each Contributor harmless for any liability
- incurred by, or claims asserted against, such Contributor by reason
- of your accepting any such warranty or additional liability.
+ anchor.attr( "href", "#" + id );
- END OF TERMS AND CONDITIONS
+ }).extendablelist();
- APPENDIX: How to apply the Flora License to your work
+ // on pagehide, remove any nested pages along with the parent page, as long as they aren't active
+ // and aren't embedded
+ if ( hasSubPages &&
+ parentPage.is( ":jqmData(external-page='true')" ) &&
+ parentPage.data( "page" ).options.domCache === false ) {
- To apply the Flora License to your work, attach the following
- boilerplate notice, with the fields enclosed by brackets "[]"
- replaced with your own identifying information. (Don't include
- the brackets!) The text should be enclosed in the appropriate
- comment syntax for the file format. We also recommend that a
- file or class name and description of purpose be included on the
- same "printed page" as the copyright notice for easier
- identification within third-party archives.
+ newRemove = function ( e, ui ) {
+ var nextPage = ui.nextPage, npURL;
- Copyright [yyyy] [name of copyright owner]
+ if ( ui.nextPage ) {
+ npURL = nextPage.jqmData( "url" );
+ if ( npURL.indexOf( parentUrl + "&" + $.mobile.subPageUrlKey ) !== 0 ) {
+ self.childPages().remove();
+ parentPage.remove();
+ }
+ }
+ };
- Licensed under the Flora License, Version 1.0 (the "License");
- you may not use this file except in compliance with the License.
- You may obtain a copy of the License at
+ // unbind the original page remove and replace with our specialized version
+ parentPage
+ .unbind( "pagehide.remove" )
+ .bind( "pagehide.remove", newRemove);
+ }
+ },
- http://floralicense.org/license/
+ // TODO sort out a better way to track sub pages of the extendable listview this is brittle
+ childPages: function () {
+ var parentUrl = this.parentPage.jqmData( "url" );
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- See the License for the specific language governing permissions and
- limitations under the License.
+ return $( ":jqmData(url^='" + parentUrl + "&" + $.mobile.subPageUrlKey + "')" );
+ }
+ });
+ //auto self-init widgets
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $( $.tizen.extendablelist.prototype.options.initSelector, e.target ).extendablelist();
+ });
- * Authors: Hyunsook Park <hyunsook.park@samsung.com>
- * Wonseop Kim <wonseop.kim@samsung.com>
- */
+}( jQuery ));
-/**
- * The gallery3d widget displays images along a curved path on a 3-dimensional coordinate system.
- * To improve performance, the size of image(s) displayed on the screen should be a square(under
- * 128X128 pixel) as possible. But if a user can't resize the images, this widget supports an image
- * resizing feature and he/she can use it with "data-thumbnail-cache" option. ("data-thumbnail-cache"
- * option resizes the gallery images under 128x128 pixels and stores the images on a local storage.
- * So when a gallery3D widget is re-launched, the widget reuse the storage and a user can improve
- * launching time. A browser or web runtime engine should support "Web Storage" feature to use that
- * option.)
- *
- * HTML Attributes:
- *
- * data-thumbnail-cache : Determines whether to cache and resize images.
+
+
+/*
+ * jQuery Mobile Widget @VERSION
*
- * APIs:
+ * This software is licensed under the MIT licence (as defined by the OSI at
+ * http://www.opensource.org/licenses/mit-license.php)
*
- * next ( void )
- * : This method moves each image forward one by one.
- * prev ( void )
- * : This method moves each image backward one by one.
- * select ( [number] )
- * : When the "select" method is called with an argument, the method selects the image of given index.
- * If the method is called with no argument, it will return the Javascript object having "src"
- * attribute having the selected image's URL.
- * add ( object or string [, number] )
- * This method adds an image to Gallery3D widget.
- * If the second argument isn't inputted, the image is added at the 0th position.
- * remove ( [number] )
- * : This method deletes an image from Gallery3d widget.
- * The argument defines the index of the image to be deleted.
- * If an argument isn't inputted, it removes current image.
- * clearThumbnailCache ( void )
- * : This method clears the cache data of all images when thumbnailCache option is set as 'true'.
- * refresh ( void )
- * : This method updates and redraws current widget.
- * empty ( void )
- * : This method removes all of images from Gallery3D widget.
- * length ( void )
- * : This method gets the number of images.
+ * ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2011 by Intel Corporation Ltd.
*
- * Events:
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
*
- * select : Triggered when an image is selected.
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
*
- * Examples:
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
*
- * <script>
- * $( "#gallery3d" ).on( "gallery3dcreate", function () {
- * $( "#gallery3d" ).gallery3d( "add", "01.jpg" );
- * });
- * </script>
- * <div id="gallery3d" data-role="gallery3d"></div>
+ * Authors: Elliot Smith <elliot.smith@intel.com>
+ * Yonghwi Park <yonghwi0324.park@samsung.com>
*/
+// fastscroll is a scrollview controller, which binds
+// a scrollview to a a list of short cuts; the shortcuts are built
+// from the text on dividers in the list. Clicking on a shortcut
+// instantaneously jumps the scrollview to the selected list divider;
+// mouse movements on the shortcut column move the scrollview to the
+// list divider matching the text currently under the touch; a popup
+// with the text currently under the touch is also displayed.
+//
+// To apply, add the attribute data-fastscroll="true" to a listview
+// (a <ul> or <ol> element inside a page). Alternatively, call
+// fastscroll() on an element.
+//
+// The closest element with class ui-scrollview-clip is used as the
+// scrollview to be controlled.
+//
+// If a listview has no dividers or a single divider, the widget won't
+// display.
+
/**
- @class Gallery3D
- The gallery3d widget displays images along a curved path on a 3-dimensional coordinate system.
- <br/><br/>To add an gallery3d widget to the application, use the following code:
+ @class fastscroll
+ The shortcut scroll widget shows a shortcut list that is bound to its parent scroll bar and respective list view. This widget is displayed as a text pop-up representing shortcuts to different list dividers in the list view. If you select a shortcut text from the shortcut scroll, the parent list view is moved to the location representing the selected shortcut.
+
+ To add a shortcut scroll widget to the application, use the following code:
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", "01.jpg" );
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
+ <div class="content" data-role="content" data-scroll="y">
+ <ul id="contacts" data-role="listview" data-fastscroll="true">
+ <li>Anton</li>
+ </ul>
+ </div>
+
+ For the shortcut scroll widget to be visible, the parent list view must have multiple list dividers.
*/
+
/**
- @property {Boolean} data-thumbnail-cache
- Determines whether to cache and resize images.
- To improve performance, the size of image(s) displayed on the screen should be a square (under 128X128 pixels).
- "data-thumbnail-cache" option resizes the gallery images under 128x128 pixels and stores the images on a local storage.
- So when a gallery3D widget is re-launched, the widget reuses the storage and the launching time can be improved.
- A browser or web runtime engine must support "Web Storage" feature to use this option.
+ @property {Boolean} data-fastscroll
+ When set to true, creates a shortcut scroll using the HTML unordered list (<ul>) element.
*/
/**
- @event select
- Triggered when an image is selected.
-
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } );
- }).on( "select", function ( event, data, index ) {
- // Handle the select event
- var urlOfImage = data.src, indexOfImage = index;
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
+ @method fastscroll
+ The shortcut scroll is created for the closest list view with the ui-scrollview-clip class.
*/
/**
- @method next
- This method moves each image forward one by one.
+ @method indexString
+ The indexString method is used to get (if no value is defined) or set the string to present the index.
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } )
- .gallery3d( "next" );
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
-*/
-/**
- @method prev
- This method moves each image backward one by one.
+ <div class="content" data-role="content" data-scroll="y">
+ ul id="contacts" data-role="listview" data-fastscroll="true">
+ <li data-role="list-divider">A</li>
+ <li>Anton</li>
+ </ul>
+ </div>
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } )
- .gallery3d( "prev" );
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
+ $(".selector").fastscroll( "indexString" [, indexAlphabet] );
*/
-/**
- @method select
- When the "select" method is called with an argument, the method selects the image of given index.
- If the method is called with no argument, it will return the Javascript object having "src" attribute having the selected image's URL.
+(function ( $, undefined ) {
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } );
- var selectedImage = $("#gallery3d"). gallery3d( "select" );
- // selectedImage = { src: "3.jpg" };
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
-*/
-/**
- @method add
- This method adds an image to Gallery3D widget.
- The first argument is a Javascript object having a "src" attribute or a string of image's path.
- The second argument is an index of images.
- If second argument isn't inputted, the image is added at the 0th position.
+ $.widget( "tizen.fastscroll", $.mobile.widget, {
+ options: {
+ initSelector: ":jqmData(fastscroll)"
+ },
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", "2.jpg", 1 );
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
-*/
-/**
- @method remove
- This method deletes an image from Gallery3d widget.
- The argument defines the index of the image to be deleted.
- If an argument isn't inputted, it removes current image.
+ _primaryLanguage: null,
+ _secondLanguage: null,
+ _dividerMap: {},
+ _defaultTime: 500,
+ _defaultDuration: 500,
+ _timer: null,
+ _isFadeOut: false,
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } );
+ _create: function () {
+ var $el = this.element,
+ self = this,
+ $popup,
+ page = $el.closest( ':jqmData(role="page")' ),
+ jumpToDivider;
- $( "#gallery3d" ).gallery3d( "remove" );
- $( "#gallery3d" ).gallery3d( "remove", 1 );
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
-*/
-/**
- @method clearThumbnailCache
- This method clears the cache data of all images when thumbnailCache option is set as 'true'
+ this.scrollview = $el.addClass( 'ui-fastscroll-target' ).closest( '.ui-scrollview-clip' );
+ this.shortcutsContainer = $( '<div class="ui-fastscroll" aria-label="Fast scroll bar, double tap to fast scroll mode" tabindex="0"/>' );
+ this.shortcutsList = $( '<ul aria-hidden="true"></ul>' );
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } );
+ // popup for the hovering character
+ this.scrollview.append($( '<div class="ui-fastscroll-popup"></div>' ) );
+ $popup = this.scrollview.find( '.ui-fastscroll-popup' );
- $( "#gallery3d" ).gallery3d( "clearThumbnailCache" );
- });
- </script>
- <div id="gallery3d" data-role="gallery3d" data-thumbnail-cache="true"></div>
-*/
-/**
- @method refresh
- This method updates and redraws current widget.
+ this.shortcutsContainer.append( this.shortcutsList );
+ this.scrollview.append( this.shortcutsContainer );
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } );
+ // find the bottom of the last item in the listview
+ this.lastListItem = $el.children().last();
- $( "#gallery3d" ).gallery3d( "refresh" );
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
-*/
-/**
- @method empty
- This method removes all of images from Gallery3D widget.
+ // remove scrollbars from scrollview
+ this.scrollview.find( '.ui-scrollbar' ).hide();
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } );
+ this.jumpToDivider = function ( divider ) {
+ // get the vertical position of the divider (so we can scroll to it)
+ var dividerY = $( divider ).position().top,
+ // find the bottom of the last list item
+ bottomOffset = self.lastListItem.outerHeight( true ) + self.lastListItem.position().top,
+ scrollviewHeight = self.scrollview.height(),
- $( "#gallery3d" ).gallery3d( "empty" );
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
-*/
-/**
- @method length
- This method gets the number of images.
+ // check that after the candidate scroll, the bottom of the
+ // last item will still be at the bottom of the scroll view
+ // and not some way up the page
+ maxScroll = bottomOffset - scrollviewHeight,
+ dstOffset;
- <script>
- $( "#gallery3d" ).on( "gallery3dcreate", function () {
- $( "#gallery3d" ).gallery3d( "add", { src: "1.jpg" } )
- .gallery3d( "add", { src: "2.jpg" } )
- .gallery3d( "add", { src: "3.jpg" } );
+ dividerY = ( dividerY > maxScroll ? maxScroll : dividerY );
+
+ // don't apply a negative scroll, as this means the
+ // divider should already be visible
+ dividerY = Math.max( dividerY, 0 );
+
+ // apply the scroll
+ self.scrollview.scrollview( 'scrollTo', 0, -dividerY );
+
+ dstOffset = self.scrollview.offset();
+ };
+
+ this.shortcutsList
+ // bind mouse over so it moves the scroller to the divider
+ .bind( 'touchstart mousedown vmousedown touchmove vmousemove vmouseover', function ( e ) {
+ // Get coords relative to the element
+ var coords = $.mobile.tizen.targetRelativeCoordsFromEvent( e ),
+ shortcutsListOffset = self.shortcutsList.offset();
+
+ if ( self._isFadeOut === true ) {
+ return;
+ }
+
+ // If the element is a list item, get coordinates relative to the shortcuts list
+ if ( e.target.tagName.toLowerCase() === "li" ) {
+ coords.x += $( e.target ).offset().left - shortcutsListOffset.left;
+ coords.y += $( e.target ).offset().top - shortcutsListOffset.top;
+ }
+
+ if ( e.target.tagName.toLowerCase() === "span" ) {
+ coords.x += $( e.target ).parent().offset().left - shortcutsListOffset.left;
+ coords.y += $( e.target ).parent().offset().top - shortcutsListOffset.top;
+ }
+
+ self.shortcutsList.find( 'li' ).each( function () {
+ var listItem = $( this );
+ $( listItem )
+ .removeClass( "ui-fastscroll-hover" )
+ .removeClass( "ui-fastscroll-hover-down" );
+ });
+ // Hit test each list item
+ self.shortcutsList.find( 'li' ).each( function () {
+ var listItem = $( this ),
+ l = listItem.offset().left - shortcutsListOffset.left,
+ t = listItem.offset().top - shortcutsListOffset.top,
+ r = l + Math.abs(listItem.outerWidth( true ) ),
+ b = t + Math.abs(listItem.outerHeight( true ) ),
+ unit,
+ baseTop,
+ baseBottom,
+ omitSet,
+ i;
+
+ if ( coords.x >= l && coords.x <= r && coords.y >= t && coords.y <= b ) {
+ if ( listItem.text() !== "." ) {
+ self._hitItem( listItem );
+ } else {
+ omitSet = listItem.data( "omitSet" );
+ unit = ( b - t ) / omitSet.length;
+ for ( i = 0; i < omitSet.length; i++ ) {
+ baseTop = t + ( i * unit );
+ baseBottom = baseTop + unit;
+ if ( coords.y >= baseTop && coords.y <= baseBottom ) {
+ self._hitOmitItem( listItem, omitSet.charAt( i ) );
+ }
+ }
+ }
+ return false;
+ }
+ return true;
+ } );
- var imagesLength = $( "#gallery3d" ).gallery3d( "length" );
- // imagesLength = 3;
- });
- </script>
- <div id="gallery3d" data-role="gallery3d"></div>
-*/
+ self._setTimer( false );
-( function ( $, document, window, undefined ) {
- function Node() {
- this.vertices = [
- -1.0, -1.0, 0.0,
- 1.0, -1.0, 0.0,
- 1.0, 1.0, 0.0,
- -1.0, 1.0, 0.0
- ];
- this.textureCoords = [
- 1.0, 0.0,
- 0.0, 0.0,
- 0.0, 1.0,
- 1.0, 1.0
- ];
- this.normalVectors = [
- 0.0, 0.0, 1.0,
- 0.0, 0.0, 1.0,
- 0.0, 0.0, 1.0,
- 0.0, 0.0, 1.0
- ];
- this.texture = null;
- this.textureBuffer = null;
- this.textureBufferItemSize = 0;
- this.mashOrder = [];
- this.mvMatrix = null;
- this.level = -1;
- this.targetLevel = 0;
- this.drawable = false;
- this.image = null;
- this.imageID = 0;
- }
+ e.preventDefault();
+ e.stopPropagation();
+ } )
+ // bind mouseout of the fastscroll container to remove popup
+ .bind( 'touchend mouseup vmouseup vmouseout', function () {
+ $popup.hide();
+ $( ".ui-fastscroll-hover" ).removeClass( "ui-fastscroll-hover" );
+ $( ".ui-fastscroll-hover-first-item" ).removeClass( "ui-fastscroll-hover-first-item" );
+ $( ".ui-fastscroll-hover-down" ).removeClass( "ui-fastscroll-hover-down" );
+ self._setTimer( true );
+ } );
- var isPreInitailization = false,
- glMatrix = {},
- VERTEX_SHADER,
- FRAGMENT_SHADER,
- GlArray32,
- GlArray16,
- preInitialize = function () {
- if ( isPreInitailization ) {
- return;
+ if ( page && !( page.is( ':visible' ) ) ) {
+ page.bind( 'pageshow', function () { self.refresh(); } );
+ } else {
+ self.refresh();
}
- window.initGlMatrix( glMatrix );
+ // refresh the list when dividers are filtered out
+ $el.bind( 'updatelayout', function () {
+ self.refresh();
+ } );
- VERTEX_SHADER = [
- "attribute vec3 aVertexPosition;",
- "attribute vec2 aTextureCoord;",
- "attribute vec3 aVertexNormal;",
- "uniform mat4 uMoveMatrix;",
- "uniform mat4 uPerspectiveMatrix;",
- "uniform mat3 nNormalMatrix;",
- "uniform vec3 uAmbientColor;",
- "uniform vec3 uLightDirection;",
- "uniform vec3 uDirectionColor;",
- "uniform vec3 uLightDirection_first;",
- "uniform vec3 uLightDirection_second;",
- "varying vec2 vTextureCoord;",
- "varying vec3 vLightWeight;",
- "varying vec4 vFogWeight;",
+ self.scrollview.bind( "scrollstart", function ( e ) {
+ self._setTimer( false );
+ }).bind( "scrollstop", function ( e ) {
+ self._setTimer( true );
+ });
+ },
- "void main(void) {",
- " vec4 v_Position = uMoveMatrix * vec4(aVertexPosition, 1.0);",
- " gl_Position = uPerspectiveMatrix * v_Position;",
- " vTextureCoord = aTextureCoord;",
- " float fog = 1.0 - ((gl_Position.z + 1.5) / 60.0);",
- " vFogWeight = clamp( vec4( fog, fog, fog, 1.0), 0.6, 1.0);",
- " vec3 transNormalVector = nNormalMatrix * aVertexNormal;",
+ _hitOmitItem: function ( listItem, text ) {
+ var self = this,
+ $popup = self.scrollview.find( '.ui-fastscroll-popup' ),
+ divider = self._dividerMap[ text ];
- " float vLightWeightFirst = 0.0;",
- " float vLightWeightSecond = max( dot(transNormalVector, uLightDirection_second), 0.0 );",
+ if ( typeof divider !== "undefined" ) {
+ self.jumpToDivider( $( divider ) );
+ }
- " vLightWeight = uAmbientColor + uDirectionColor * vLightWeightSecond;",
- "}"
- ].join( "\n" );
+ $popup.text( text )
+ .css( { marginLeft: -( $popup.outerWidth() / 2 ),
+ marginTop: -( $popup.outerHeight() / 2 ),
+ padding: $popup.css( "paddingTop" ) } )
+ .width( $popup.height() )
+ .show();
- FRAGMENT_SHADER = [
- "precision mediump float;",
- "varying vec2 vTextureCoord;",
- "varying vec3 vLightWeight;",
- "uniform sampler2D uSampler;",
- "varying vec4 vFogWeight;",
+ $( listItem ).addClass( "ui-fastscroll-hover" );
+ if ( listItem.index() === 0 ) {
+ $( listItem ).addClass( "ui-fastscroll-hover-first-item" );
+ }
+ $( listItem ).siblings().eq( listItem.index() ).addClass( "ui-fastscroll-hover-down" );
+ },
- "void main(void) {",
- " vec4 TextureColor;",
- " if ( vTextureCoord.s <= 0.01 || vTextureCoord.s >= 0.99 || vTextureCoord.t <= 0.01 || vTextureCoord.t >= 0.99 ) {",
- " TextureColor = vec4(1.0, 1.0, 1.0, 0.5);",
- " } else {",
- " TextureColor = texture2D(uSampler, vec2(vTextureCoord.s, vTextureCoord.t));",
- " }",
- " TextureColor *= vFogWeight;",
- " gl_FragColor = vec4(TextureColor.rgb * vLightWeight, TextureColor.a);",
- "}"
- ].join( "\n" );
+ _hitItem: function ( listItem ) {
+ var self = this,
+ $popup = self.scrollview.find( '.ui-fastscroll-popup' ),
+ text = listItem.text(),
+ divider;
- GlArray32 = ( typeof window.Float32Array !== "undefined" ?
- window.Float32Array :
- ( typeof window.WebGLFloatArray !== "undefined" ? window.WebGLFloatArray : Array ) );
+ if ( text === "#" ) {
+ divider = self._dividerMap.number;
+ } else {
+ divider = self._dividerMap[ text ];
+ }
- GlArray16 = ( typeof window.Uint16Array !== "undefined" ? window.Uint16Array : Array );
+ if ( typeof divider !== "undefined" ) {
+ self.jumpToDivider( $( divider ) );
+ }
- isPreInitailization = true;
- },
- degreeToRadian = function ( degree ) {
- return degree * Math.PI / 180;
- },
- getContext3D = function ( canvas ) {
- var gl, i,
- contextNames = [ "experimental-webgl", "webkit-3d", "webgl", "moz-webgl" ];
+ $popup.text( text )
+ .css( { marginLeft: -( $popup.outerWidth() / 2 ),
+ marginTop: -( $popup.outerHeight() / 2 ),
+ padding: $popup.css( "paddingTop" ) } )
+ .width( $popup.height() )
+ .show();
- for ( i = 0; i < contextNames.length; i += 1 ) {
- try {
- gl = canvas.getContext( contextNames[i] );
- if ( gl ) {
- break;
- }
- } catch ( e ) {
- $( canvas ).html( "Unfortunately, there's a WebGL compatibility problem. </br> You may want to check your system settings." );
- return;
- }
+ $( listItem ).addClass( "ui-fastscroll-hover" );
+ if ( listItem.index() === 0 ) {
+ $( listItem ).addClass( "ui-fastscroll-hover-first-item" );
}
- return gl;
- },
- requestAnimationFrame = function ( callback ) {
- var id = window.setTimeout( callback, 1000 / 60 );
- return id;
- },
- cancelAnimationFrame = function ( id ) {
- window.clearTimeout( id );
- };
-
- $.widget( "tizen.gallery3d", $.mobile.widget, {
- options: {
- thumbnailCache: false
+ $( listItem ).siblings().eq( listItem.index() ).addClass( "ui-fastscroll-hover-down" );
},
- _MAX_ITEM_COUNT: 28,
- _ANIMATION_END: 999,
- _DURATION_DEFAULT: 300,
- _DURATION_FIRST: 1600,
- _VIEWPORT_WIDTH: 1024,
- _VIEWPORT_HEIGHT: 456,
- _DIRECTION_LEFT: -1,
- _DIRECTION_RIGHT: +1,
+ _focusItem: function ( listItem ) {
+ var self = this,
+ $popup = self.scrollview.find( '.ui-fastscroll-popup' );
- _gl: null,
- _shaderProgram : null,
- _positionBuffer : null,
- _textureCoordBuffer : null,
- _normalVectorBuffer : null,
- _nodes: null,
- _pMatrix : null,
- _animationID: 0,
- _dragInterval : 0,
- _startTime : 0,
- _sumTime : 0,
- _lightsPositionStack : [
- [0.0, 0.0, -1.0], // back
- [-0.2, 0.0, 0.7] // front
- ],
- _path: null,
- _swipeThresholdOfBasetimeGap: ( $.support.touch ? 30 : 70 ),
- _swipeThresholdOfSensitivity: ( $.support.touch ? 2.0 : 10.0 ),
- _canvas: null,
- _imageList: [],
- _maxDrawLength: 0,
- _firstImageNumber: 0,
- _lastImageNumber: 0,
+ listItem.focusin( function ( e ) {
+ self.shortcutsList.attr( "aria-hidden", false );
+ self._hitItem( listItem );
+ self._setTimer( false );
+ }).focusout( function ( e ) {
+ self.shortcutsList.attr( "aria-hidden", true );
+ $popup.hide();
+ $( ".ui-fastscroll-hover" ).removeClass( "ui-fastscroll-hover" );
+ $( ".ui-fastscroll-hover-first-item" ).removeClass( "ui-fastscroll-hover-first-item" );
+ $( ".ui-fastscroll-hover-down" ).removeClass( "ui-fastscroll-hover-down" );
+ self._setTimer( true );
+ });
+ },
- _create: function () {
+ _contentHeight: function () {
var self = this,
- view = self.element,
- option = self.options;
+ $content = $( '.ui-scrollview-clip' ),
+ header = null,
+ footer = null,
+ paddingValue = 0,
+ clipSize = $( window ).height();
- preInitialize();
+ if ( $content.hasClass( "ui-content" ) ) {
+ paddingValue = parseInt( $content.css( "padding-top" ), 10 );
+ clipSize = clipSize - ( paddingValue || 0 );
+ paddingValue = parseInt( $content.css( "padding-bottom" ), 10 );
+ clipSize = clipSize - ( paddingValue || 0 );
+ header = $content.siblings( ".ui-header:visible" );
+ footer = $content.siblings( ".ui-footer:visible" );
- self._canvas = $( "<canvas class='ui-gallery3d-canvas'></canvas>" );
+ if ( header ) {
+ if ( header.outerHeight( true ) === null ) {
+ clipSize = clipSize - ( $( ".ui-header" ).outerHeight() || 0 );
+ } else {
+ clipSize = clipSize - header.outerHeight( true );
+ }
+ }
+ if ( footer ) {
+ clipSize = clipSize - footer.outerHeight( true );
+ }
+ } else {
+ clipSize = $content.height();
+ }
+ return clipSize;
+ },
- view.addClass( "ui-gallery3d" ).append( self._canvas );
- self._addBehavier();
+ _omit: function ( numOfItems, maxNumOfItems ) {
+ var maxGroupNum = parseInt( ( maxNumOfItems - 1 ) / 2, 10 ),
+ numOfExtraItems = numOfItems - maxNumOfItems,
+ groupPos = [],
+ omitInfo = [],
+ groupPosLength,
+ group,
+ size,
+ i;
- self._dragInterval = 1000 / 30; // 30fps
+ if ( ( maxNumOfItems < 3 ) || ( numOfItems <= maxNumOfItems ) ) {
+ return;
+ }
- $.each( self.options, function ( key, value ) {
- self.options[ key ] = undefined;
- self._setOption( key, value );
- });
- },
+ if ( numOfExtraItems >= maxGroupNum ) {
+ size = 2;
+ group = 1;
+ groupPosLength = maxGroupNum;
+ } else {
+ size = maxNumOfItems / ( numOfExtraItems + 1 );
+ group = size;
+ groupPosLength = numOfExtraItems;
+ }
- destroy: function () {
- this._final();
- $.mobile.widget.prototype.destroy.call( this );
- },
+ for ( i = 0; i < groupPosLength; i++ ) {
+ groupPos.push( parseInt( group, 10 ) );
+ group += size;
+ }
- _setOption: function ( key, value ) {
- switch ( key ) {
- case "thumbnailCache" :
- if ( typeof value === "string" ) {
- value = ( value === "true" ) ? true : false;
- } else {
- value = !!value;
- }
- this._reset();
- break;
+ for ( i = 0; i < maxNumOfItems; i++ ) {
+ omitInfo.push( 1 );
}
- $.mobile.widget.prototype._setOption.call( this, key, value );
+ for ( i = 0; i < numOfExtraItems; i++ ) {
+ omitInfo[ groupPos[ i % maxGroupNum ] ]++;
+ }
+
+ return omitInfo;
},
- _init: function ( canvas ) {
+ _createDividerMap: function () {
var self = this,
- pathPoints = [
- [40, 0, -48],
- [-12, 0, -40], // contorl Point of Point1
- [24, 0, -9], // contorl Point of Point2
- [-5, 0, -5]
- ],
+ primaryCharacterSet = self._primaryLanguage ? self._primaryLanguage.replace( /,/g, "" ) : null,
+ secondCharacterSet = self._secondLanguage ? self._secondLanguage.replace( /,/g, "" ) : null,
+ numberSet = "0123456789",
+ dividers = self.element.find( '.ui-li-divider' ),
+ map = {},
+ matchToDivider,
+ makeCharacterSet,
+ indexChar,
i;
- canvas = canvas || self._canvas;
+ matchToDivider = function ( index, divider ) {
+ if ( $( divider ).text() === indexChar ) {
+ map[ indexChar ] = divider;
+ }
+ };
- if ( !canvas ) {
- return;
- }
+ makeCharacterSet = function ( index, divider ) {
+ primaryCharacterSet += $( divider ).text();
+ };
- self._gl = self._gl || self._initGL( canvas[0] );
- if ( !self._gl ) {
- return;
+ if ( primaryCharacterSet === null ) {
+ primaryCharacterSet = "";
+ dividers.each( makeCharacterSet );
}
- if ( !self._imageList ) {
- return;
+ for ( i = 0; i < primaryCharacterSet.length; i++ ) {
+ indexChar = primaryCharacterSet.charAt( i );
+ dividers.each( matchToDivider );
}
- self._shaderProgram = self._shaderProgram || self._initShader( self._gl );
- if ( !self._shaderProgram ) {
- return;
+ if ( secondCharacterSet !== null ) {
+ for ( i = 0; i < secondCharacterSet.length; i++ ) {
+ indexChar = secondCharacterSet.charAt( i );
+ dividers.each( matchToDivider );
+ }
}
- if ( self._imageList.length > self._MAX_ITEM_COUNT ) {
- self._firstImageNumber = self._imageList.length - 1;
- self._lastImageNumber = self._MAX_ITEM_COUNT - 1;
- }
+ dividers.each( function ( index, divider ) {
+ if ( numberSet.search( $( divider ).text() ) !== -1 ) {
+ map.number = divider;
+ return false;
+ }
+ });
- self._nodes = self._initBuffers( self._gl, self._shaderProgram );
+ self._dividerMap = map;
+ },
- self._initTextures( self._gl, self._nodes );
+ _setTimer: function ( start ) {
+ var self = this;
- self._path = $.motionpath( "bezier2d", {
- points: pathPoints,
- maxLevel: self._MAX_ITEM_COUNT
- } );
- for ( i = 0; i < self._nodes.length; i += 1 ) {
- self._path.levels[i] = self._path.levels[i + 1] || 0;
- self._nodes[i].level = i;
+ if ( start === true ) {
+ self._timer = setTimeout( function () {
+ self._isFadeOut = true;
+ self.shortcutsContainer.fadeOut( self._defaultDuration, function () {
+ self._isFadeOut = false;
+ });
+ }, self._defaultTime );
+ } else {
+ if ( self._timer !== null ) {
+ clearTimeout( self._timer );
+ }
+ self.shortcutsContainer.show();
}
},
- _final: function ( canvas ) {
+ indexString: function ( indexAlphabet ) {
var self = this,
- gl = self._gl;
+ characterSet = [];
- if ( !gl ) {
- return;
+ if ( typeof indexAlphabet === "undefined" ) {
+ return self._primaryLanguage + ":" + self._secondLanguage;
}
- canvas = canvas || self._canvas;
-
- $( self._nodes ).each( function ( i ) {
- var node = self._nodes[i];
- gl.deleteTexture( node.texture );
- node.texture = null;
- });
- self._nodes = null;
-
- gl.deleteBuffer( self._positionBuffer );
- self._positionBuffer = null;
- gl.deleteBuffer( self._textureCoordBuffer );
- self._textureCoordBuffer = null;
- gl.deleteBuffer( self._normalVectorBuffer );
- self._normalVectorBuffer = null;
-
- $.webgl.shader.deleteShaders( gl );
- gl.deleteProgram( self._shaderProgram );
- self._shaderProgram = null;
-
- self._gl = gl = null;
+ characterSet = indexAlphabet.split( ":" );
+ self._primaryLanguage = characterSet[ 0 ];
+ if ( characterSet.length === 2 ) {
+ self._secondLanguage = characterSet[ 1 ];
+ }
},
- _addBehavier : function () {
+ refresh: function () {
var self = this,
- view = self.element,
- canvas = self._canvas,
- touchStartEvt = ( $.support.touch ? "touchstart" : "mousedown" ),
- touchMoveEvt = ( $.support.touch ? "touchmove" : "mousemove" ) + ".gallery3d",
- touchEndEvt = ( $.support.touch ? "touchend" : "mouseup" ) + ".gallery3d",
- touchLeaveEvt = ( $.support.touch ? "touchleave" : "mouseout" ) + ".gallery3d";
+ primaryCharacterSet = self._primaryLanguage ? self._primaryLanguage.replace( /,/g, "" ) : null,
+ secondCharacterSet = self._secondLanguage ? self._secondLanguage.replace( /,/g, "" ) : null,
+ contentHeight = self._contentHeight(),
+ shapItem = $( '<li tabindex="0" aria-label="double to move Number list"><span aria-hidden="true">#</span><span aria-label="Number"/></li>' ),
+ omitIndex = 0,
+ makeCharacterSet,
+ makeOmitSet,
+ itemHandler,
+ containerHeight,
+ shortcutsItems,
+ shortcutItem,
+ shortcutsTop,
+ minClipHeight,
+ maxNumOfItems,
+ numOfItems,
+ minHeight,
+ padding,
+ omitInfo,
+ dividers,
+ listItems,
+ emptySize,
+ correction,
+ indexChar,
+ lastIndex,
+ seconds,
+ height,
+ size,
+ i;
- canvas.on( "webglcontextlost", function ( e ) {
- e.preventDefault();
- }).on( "webglcontextrestored", function ( e ) {
- self._init();
- }).on( touchStartEvt, function ( e ) {
- var i = 0,
- startX = 0,
- deltaMaxSteps = 20,
- deltas = [ deltaMaxSteps ],
- deltaTimes = [ deltaMaxSteps ],
- deltaIndex = 0,
- dragValue = 0,
- dragDirection = false,
- prevTime = 0;
+ makeCharacterSet = function ( index, divider ) {
+ primaryCharacterSet += $( divider ).text();
+ };
- e.preventDefault();
- e.stopPropagation();
+ makeOmitSet = function ( index, length ) {
+ var count,
+ omitSet = "";
- if ( self._imageList.length <= 1 ) {
- return;
+ for ( count = 0; count < length; count++ ) {
+ omitSet += primaryCharacterSet[ index + count ];
}
- self._stop();
+ return omitSet;
+ };
- startX = $.support.touch ? e.originalEvent.changedTouches[0].pageX : e.pageX;
- prevTime = $.now();
+ itemHandler = function ( e ) {
+ var text = $( this ).text(),
+ matchDivider = self._dividerMap[ text ];
- for ( i = 0; i < deltaMaxSteps; i += 1 ) {
- deltas[i] = startX;
- deltaTimes[i] = $.now();
+ if ( typeof matchDivider !== "undefined" ) {
+ $( matchDivider ).next().focus();
}
+ };
- deltaIndex += 1;
+ self._createDividerMap();
- view.on( touchMoveEvt, function ( e ) {
- var x, dx, interval;
+ self.shortcutsList.find( 'li' ).remove();
- e.preventDefault();
- e.stopPropagation();
+ // get all the dividers from the list and turn them into shortcuts
+ dividers = self.element.find( '.ui-li-divider' );
- x = $.support.touch ? e.originalEvent.changedTouches[0].pageX : e.pageX;
- dx = startX - x;
+ // get all the list items
+ listItems = self.element.find('li').not('.ui-li-divider');
- deltas[deltaIndex] = x;
- deltaTimes[deltaIndex] = $.now();
- interval = deltaTimes[deltaIndex] - prevTime;
+ // only use visible dividers
+ dividers = dividers.filter( ':visible' );
+ listItems = listItems.filter( ':visible' );
- deltaIndex = ( deltaIndex + 1 ) % deltaMaxSteps;
+ if ( dividers.length < 2 ) {
+ self.shortcutsList.hide();
+ return;
+ }
- // Validation of drag
- if ( Math.abs( dx ) >= 10 && interval >= self._dragInterval ) {
- if ( dragDirection !== ( ( dx < 0 ) ? self._DIRECTION_RIGHT : self._DIRECTION_LEFT ) ) {
- dragValue = 0;
- dragDirection = ( dx < 0 ) ? self._DIRECTION_RIGHT : self._DIRECTION_LEFT;
- }
+ self.shortcutsList.show();
+ self.lastListItem = listItems.last();
+ self.shortcutsList.append( shapItem );
+ self._focusItem( shapItem );
- dragValue += Math.abs( dx ) / 100;
- if ( dragValue >= 1 ) {
- self._setPosition( self._ANIMATION_END, dragDirection );
- dragValue = 0;
- } else {
- self._setPosition( dragValue, dragDirection );
- }
- self._drawScene();
- startX = x;
- prevTime = $.now();
- }
- }).on( touchEndEvt, function ( e ) {
- var baseTime = 0,
- recent = -1,
- index = 0,
- previous = 0,
- baseTimeRatio = 0,
- fx = 0,
- lastX = 0,
- velocityX = 0,
- dx = 0,
- isSwipe = true,
- direction;
+ if ( primaryCharacterSet === null ) {
+ primaryCharacterSet = "";
+ dividers.each( makeCharacterSet );
+ }
- e.preventDefault();
- e.stopPropagation();
+ padding = parseInt( shapItem.css( "padding" ), 10 );
+ minHeight = shapItem.height() + ( padding * 2 );
+ maxNumOfItems = parseInt( ( contentHeight / minHeight ) - 1, 10 );
+ numOfItems = primaryCharacterSet.length;
- // Validation of swipe
- baseTime = $.now() - self._swipeThresholdOfBasetimeGap;
- lastX = $.support.touch ? e.originalEvent.changedTouches[0].pageX : e.pageX;
- dx = startX - lastX;
- startX = 0;
- for ( i = 0; i < deltaMaxSteps; i += 1 ) {
- index = ( deltaIndex + i ) % deltaMaxSteps;
- if ( deltaTimes[index] > baseTime ) {
- recent = index;
- break;
- }
- }
- if ( recent < 0 ) {
- isSwipe = false;
- }
+ maxNumOfItems = secondCharacterSet ? maxNumOfItems - 2 : maxNumOfItems;
- if ( isSwipe ) {
- previous = recent;
- for ( i = 0; i < deltaMaxSteps; i += 1 ) {
- previous = ( previous - 1 + deltaMaxSteps ) % deltaMaxSteps;
- if ( deltaTimes[previous] < deltaTimes[recent] ) {
- break;
- }
- }
- // too slow or too fast
- if ( i === deltaMaxSteps || baseTime < deltaTimes[previous] ) {
- isSwipe = false;
- }
- }
+ if ( maxNumOfItems < 3 ) {
+ shapItem.remove();
+ return;
+ }
- if ( isSwipe ) {
- baseTimeRatio = ( baseTime - deltaTimes[previous] ) / ( deltaTimes[recent] - deltaTimes[previous] );
- fx = ( 1.0 - baseTimeRatio ) * deltas[previous] + baseTimeRatio * deltas[recent];
- if ( Math.abs( fx - lastX ) < self._swipeThresholdOfSensitivity ) {
- fx = lastX;
- }
- velocityX = parseInt( ( lastX - fx ) / ( $.now() - baseTime ), 10 );
- }
+ omitInfo = self._omit( numOfItems, maxNumOfItems );
- if ( isSwipe && velocityX ) {
- direction = ( velocityX < 0 ) ? self._DIRECTION_LEFT : self._DIRECTION_RIGHT;
- self._run( direction, Math.abs( velocityX ), dragValue );
- } else if ( dragDirection !== 0 && dragValue ) {
- self._animate( null, self._DURATION_DEFAULT * ( 1 - dragValue ), dragDirection, 0, dragValue );
- }
+ for ( i = 0; i < primaryCharacterSet.length; i++ ) {
+ indexChar = primaryCharacterSet.charAt( i );
+ shortcutItem = $( '<li tabindex="0" aria-label="double to move ' + indexChar + ' list">' + indexChar + '</li>' );
- view.unbind( ".gallery3d" );
- }).on( touchLeaveEvt, function ( e ) {
- view.trigger( touchEndEvt );
- });
- });
- },
+ self._focusItem( shortcutItem );
- // ----------------------------------------------------------
- // WebGL
- // ----------------------------------------------------------
- _initGL: function ( canvas ) {
- var self = this,
- mat4 = glMatrix.mat4,
- gl;
+ if ( typeof omitInfo !== "undefined" && omitInfo[ omitIndex ] > 1 ) {
+ shortcutItem = $( '<li>.</li>' );
+ shortcutItem.data( "omitSet", makeOmitSet( i, omitInfo[ omitIndex ] ) );
+ i += omitInfo[ omitIndex ] - 1;
+ } else {
+ shortcutItem.bind( 'vclick', itemHandler );
+ }
- gl = getContext3D( canvas );
- if ( !gl ) {
- return null;
+ shapItem.before( shortcutItem );
+ omitIndex++;
}
- gl.enable( gl.BLEND );
- gl.blendFunc( gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA );
-
- gl.enable( gl.DEPTH_TEST );
- gl.depthFunc( gl.LEQUAL );
-
- canvas.width = self._VIEWPORT_WIDTH;
- canvas.height = self._VIEWPORT_HEIGHT;
- gl.viewportWidth = canvas.width;
- gl.viewportHeight = canvas.height;
- gl.viewport( 0, 0, gl.viewportWidth, gl.viewportHeight );
- self._pMatrix = mat4.create();
- mat4.perspective( 40, gl.viewportWidth / gl.viewportHeight, 0.1, 10000.0, self._pMatrix );
+ if ( secondCharacterSet !== null ) {
+ lastIndex = secondCharacterSet.length - 1;
+ seconds = [];
- gl.clearColor( 0.15, 0.15, 0.15, 1.0 );
- gl.clear( gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT );
+ seconds.push( secondCharacterSet.charAt( 0 ) );
+ seconds.push( secondCharacterSet.charAt( lastIndex ) );
- return gl;
- },
+ for ( i = 0; i < seconds.length; i++ ) {
+ indexChar = seconds[ i ];
+ shortcutItem = $( '<li tabindex="0" aria-label="double to move ' + indexChar + ' list">' + indexChar + '</li>' );
- _initShader : function ( gl ) {
- var self = this,
- shaderProgram;
+ self._focusItem( shortcutItem );
+ shortcutItem.bind( 'vclick', itemHandler );
+ shapItem.before( shortcutItem );
+ }
+ }
- shaderProgram = $.webgl.shader.addShaderProgram( self._gl, VERTEX_SHADER, FRAGMENT_SHADER );
- gl.useProgram( shaderProgram );
+ containerHeight = self.shortcutsContainer.outerHeight();
+ emptySize = contentHeight - containerHeight;
+ shortcutsItems = self.shortcutsList.children();
+ size = parseInt( emptySize / shortcutsItems.length, 10 );
+ correction = emptySize - ( shortcutsItems.length * size );
- shaderProgram.vertexPositionAttr = gl.getAttribLocation( shaderProgram, "aVertexPosition" );
- gl.enableVertexAttribArray( shaderProgram.vertexPositionAttr );
+ if ( emptySize > 0 ) {
+ shortcutsItems.each( function ( index, item ) {
+ height = $( item ).height() + size;
+ if ( correction !== 0 ) {
+ height += 1;
+ correction -= 1;
+ }
+ $( item ).css( {
+ height: height,
+ lineHeight: height + "px"
+ } );
+ } );
+ }
- shaderProgram.textureCoordAttr = gl.getAttribLocation( shaderProgram, "aTextureCoord" );
- gl.enableVertexAttribArray( shaderProgram.textureCoordAttr );
+ // position the shortcut flush with the top of the first list divider
+ shortcutsTop = dividers.first().position().top;
+ self.shortcutsContainer.css( 'top', shortcutsTop );
- // Set light normal vectors for lighting~
- shaderProgram.vertexNormalAttr = gl.getAttribLocation( shaderProgram, "aVertexNormal" );
- gl.enableVertexAttribArray( shaderProgram.vertexNormalAttr );
+ // make the scrollview clip tall enough to show the whole of the shortcutslist
+ minClipHeight = shortcutsTop + self.shortcutsContainer.outerHeight() + 'px';
+ self.scrollview.css( 'min-height', minClipHeight );
- shaderProgram.perspectiveMU = gl.getUniformLocation( shaderProgram, "uPerspectiveMatrix");
- shaderProgram.transformMU = gl.getUniformLocation( shaderProgram, "uMoveMatrix");
- shaderProgram.sampleUniform = gl.getUniformLocation( shaderProgram, "uSampler");
+ self._setTimer( false );
+ self._setTimer( true );
+ }
+ } );
- // Set light variables~
- shaderProgram.normalMU = gl.getUniformLocation( shaderProgram, "nNormalMatrix");
- shaderProgram.ambientColorU = gl.getUniformLocation( shaderProgram, "uAmbientColor");
- shaderProgram.lightDirU_first = gl.getUniformLocation( shaderProgram, "uLightDirection_first");
- shaderProgram.lightDirU_second = gl.getUniformLocation( shaderProgram, "uLightDirection_second");
- shaderProgram.directionColorU = gl.getUniformLocation( shaderProgram, "uDirectionColor");
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $( $.tizen.fastscroll.prototype.options.initSelector, e.target )
+ .not( ":jqmData(role='none'), :jqmData(role='nojs')" )
+ .fastscroll();
+ } );
- return shaderProgram;
- },
+ $( window ).bind( "resize orientationchange", function ( e ) {
+ $( ".ui-page-active .ui-fastscroll-target" ).fastscroll( "refresh" );
+ } );
+} ( jQuery ) );
- _initBuffers: function ( gl, shaderProgram ) {
- var self = this,
- i = 0,
- mashBase = 0,
- vertices = [],
- textureCoords = [],
- normalVectors = [],
- nodes = [],
- maxDrawLength = self._MAX_ITEM_COUNT;
- for ( i = 0; i < self._imageList.length + 1; i += 1 ) {
- nodes[i] = new Node();
- $.merge( vertices, nodes[i].vertices );
- $.merge( textureCoords, nodes[i].textureCoords );
- $.merge( normalVectors, nodes[i].normalVectors );
- nodes[i].textureBuffer = gl.createBuffer();
- gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, nodes[i].textureBuffer );
- mashBase = i * 4;
- nodes[i].meshOrder = [
- mashBase, mashBase + 1, mashBase + 2,
- mashBase + 2, mashBase + 3, mashBase
- ];
- gl.bufferData( gl.ELEMENT_ARRAY_BUFFER, new GlArray16( nodes[i].meshOrder ), gl.STATIC_DRAW );
- gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, null ); // release buffer memory
- nodes[i].textureBufferItemSize = 6;
- }
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software" ),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ */
- self._positionBuffer = $.webgl.buffer.attribBufferData( gl, new GlArray32( vertices ) );
- self._positionBuffer.itemSize = 3;
+// most of following codes are derived from jquery.mobile.scrollview.js
+(function ( $, window, document, undefined ) {
- self._textureCoordBuffer = $.webgl.buffer.attribBufferData( gl, new GlArray32( textureCoords ) );
- self._textureCoordBuffer.itemSize = 2;
+ function circularNum( num, total ) {
+ var n = num % total;
+ if ( n < 0 ) {
+ n = total + n;
+ }
+ return n;
+ }
- self._normalVectorBuffer = $.webgl.buffer.attribBufferData( gl, new GlArray32( normalVectors ) ); // Vertex's normal vector for Direction light
- self._normalVectorBuffer.itemSize = 3;
+ function setElementTransform( $ele, x, y ) {
+ var v = "translate3d( " + x + "," + y + ", 0px)";
+ $ele.css({
+ "-ms-transform": v,
+ "-o-transform": v,
+ "-moz-transform": v,
+ "-webkit-transform": v,
+ "transform": v
+ } );
+ }
- // Ambient light
- gl.uniform3f( shaderProgram.ambientColorU, 0.1, 0.1, 0.1 );
- // Direcntion light
- gl.uniform3f( shaderProgram.directionColorU, 1.0, 1.0, 1.0 );
+ function MomentumTracker( options ) {
+ this.options = $.extend( {}, options );
+ this.easing = "easeOutQuad";
+ this.reset();
+ }
- return nodes;
- },
+ var tstates = {
+ scrolling : 0,
+ done : 1
+ };
- // ----------------------------------------------------------
- // Texture
- // ----------------------------------------------------------
- _initTextures: function ( gl, nodes ) {
- var self = this;
+ function getCurrentTime() {
+ return Date.now();
+ }
- $( nodes ).each( function ( i ) {
- var node = nodes[i],
- url;
+ $.extend( MomentumTracker.prototype, {
+ start: function ( pos, speed, duration ) {
+ this.state = ( speed != 0 ) ? tstates.scrolling : tstates.done;
+ this.pos = pos;
+ this.speed = speed;
+ this.duration = duration;
- if ( !self._imageList[i] ) {
- return false;
- }
+ this.fromPos = 0;
+ this.toPos = 0;
- url = self._imageList[i].src;
- node.texture = gl.createTexture();
- self._loadImage( url, i, i, gl, nodes );
- });
+ this.startTime = getCurrentTime();
},
- _loadImage: function ( url, i, imageID, gl, nodes ) {
- var self = this,
- isMipmap = false,
- image,
- node;
+ reset: function () {
+ this.state = tstates.done;
+ this.pos = 0;
+ this.speed = 0;
+ this.duration = 0;
+ },
- gl = gl || self._gl;
- nodes = nodes || self._nodes;
- isMipmap = isMipmap || false;
- node = nodes[i];
- node.image = node.image || new Image();
+ update: function () {
+ var state = this.state,
+ duration,
+ elapsed,
+ dx,
+ x;
- $( node.image ).one( "load", function ( e ) {
- self._bindTexture( gl, node, this, isMipmap );
- node.imageID = imageID;
+ if ( state == tstates.done ) {
+ return this.pos;
+ }
- if ( !self._animationID ) {
- self._setPosition( 0, 0 );
- }
- });
+ duration = this.duration;
+ elapsed = getCurrentTime() - this.startTime;
+ elapsed = elapsed > duration ? duration : elapsed;
- if ( self.options.thumbnailCache ) {
- $.imageloader.getThumbnail( url, function ( result ) {
- if ( result === "NOT_FOUND_ERR" ) {
- $.imageloader.setThumbnail( url, function ( result ) {
- if ( result && result.length > 30 ) {
- node.image.src = result;
- isMipmap = true;
- } else {
- node.image.src = url;
- }
- });
- } else if ( result && result.length > 30 ) {
- node.image.src = result;
- isMipmap = true;
- } else {
- node.image.src = url;
- }
- });
- } else {
- node.image.src = url;
- }
- },
+ dx = this.speed * ( 1 - $.easing[this.easing](elapsed / duration, elapsed, 0, 1, duration ) );
- _bindTexture: function ( gl, node, image, isMipmap ) {
- if ( !node || !node.texture ) {
- return;
+ x = this.pos + dx;
+ this.pos = x;
+
+ if ( elapsed >= duration ) {
+ this.state = tstates.done;
}
- gl.pixelStorei( gl.UNPACK_FLIP_Y_WEBGL, true );
+ return this.pos;
+ },
- gl.bindTexture( gl.TEXTURE_2D, node.texture );
- gl.texImage2D( gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, image );
+ done: function () {
+ return this.state == tstates.done;
+ },
- if ( isMipmap ) {
- gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR );
- gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR_MIPMAP_NEAREST );
- gl.generateMipmap( gl.TEXTURE_2D );
- } else {
- gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR );
- gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR );
- }
+ getPosition: function () {
+ return this.pos;
+ }
+ } );
- gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE );
- gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE );
+ jQuery.widget( "mobile.circularview", jQuery.mobile.widget, {
+ options: {
+ fps: 60,
- node.texture.loaded = true;
+ scrollDuration: 2000,
- // release texture memory
- gl.bindTexture( gl.TEXTURE_2D, null );
- },
+ moveThreshold: 10,
+ moveIntervalThreshold: 150,
- // ----------------------------------------------------------
- // rendering
- // ----------------------------------------------------------
- _setPosition: function ( progress, direction ) {
- var self = this,
- mat4 = glMatrix.mat4,
- nodes = self._nodes,
- imageList = self._imageList,
- imageListLength = imageList.length,
- itemCount = self._MAX_ITEM_COUNT,
- displayLength = ( imageListLength > itemCount ) ? itemCount : imageListLength,
- nextLevelLenth = 0,
- i = 0,
- t = 0,
- position = 0,
- angle = 0,
- current = 0,
- next = 0,
- nextLevel = 0,
- path = self._path,
- nextImageID = 0;
+ startEventName: "scrollstart",
+ updateEventName: "scrollupdate",
+ stopEventName: "scrollstop",
- nextLevelLenth = ( direction >= 0 ) ? displayLength + 1 : displayLength;
+ eventType: $.support.touch ? "touch" : "mouse",
- if ( !nodes[i].level ) {
- nodes[i].level = displayLength;
- }
+ delayedClickSelector: "a, .ui-btn",
+ delayedClickEnabled: false
+ },
- for ( i = 0; i < displayLength; i += 1 ) {
- if ( !nodes[i].mvMatrix ) {
- nodes[i].mvMatrix = mat4.create();
- }
+ _makePositioned: function ( $ele ) {
+ if ( $ele.css( 'position' ) == 'static' ) {
+ $ele.css( 'position', 'relative' );
+ }
+ },
- if ( direction > 0 && nodes[i].level >= displayLength ) {
- nodes[i].level = 0;
- }
+ _create: function () {
+ var self = this;
- current = path.levels[nodes[i].level];
- nextLevel = ( nodes[i].level + nextLevelLenth + direction ) % nextLevelLenth;
- next = path.levels[nextLevel];
+ this._items = $( this.element ).jqmData('list');
+ this._$clip = $( this.element ).addClass( "ui-scrollview-clip" );
+ this._$clip.wrapInner( '<div class="ui-scrollview-view"></div>' );
+ this._$view = $('.ui-scrollview-view', this._$clip );
+ this._$list = $( 'ul', this._$clip );
- if ( imageListLength > itemCount ) {
- if ( direction > 0 && nextLevel === 1
- && self._firstImageNumber !== nodes[i].imageID ) {
- self._loadImage( imageList[self._firstImageNumber].src, i, self._firstImageNumber );
- } else if ( direction < 0 && nextLevel === nextLevelLenth - 1
- && self._lastImageNumber !== nodes[i].imageID ) {
- self._loadImage( imageList[self._lastImageNumber].src, i, self._lastImageNumber );
- }
- }
+ this._$clip.css( "overflow", "hidden" );
+ this._makePositioned( this._$clip );
- mat4.identity( nodes[i].mvMatrix );
- mat4.translate( nodes[i].mvMatrix, [-2.0, -2.0, 1.0] );
- mat4.rotate( nodes[i].mvMatrix, degreeToRadian( 19 ), [1, 0, 0] );
+ this._$view.css( "overflow", "hidden" );
+ this._tracker = new MomentumTracker( this.options );
- t = ( current + ( next - current ) * ( ( progress > 1 ) ? 1 : progress ) );
+ this._timerInterval = 1000 / this.options.fps;
+ this._timerID = 0;
- if ( progress >= self._ANIMATION_END ) {
- nodes[i].level = nextLevel || displayLength;
- t = path.levels[nodes[i].level];
- }
+ this._timerCB = function () { self._handleMomentumScroll(); };
- if ( ( progress < self._ANIMATION_END )
- && ( direction <= 0 && nodes[i].level < 1 ) ) {
- nodes[i].drawable = false;
- } else {
- nodes[i].drawable = true;
- }
+ this.refresh();
- if ( progress === self._ANIMATION_END && nodes[i].level === 1 ) {
- self.element.trigger( "select", imageList[ nodes[i].imageID ], nodes[i].imageID );
- }
+ this._addBehaviors();
+ },
- position = path.getPosition( t );
- angle = path.getAngle( t );
+ reflow: function () {
+ var xy = this.getScrollPosition();
+ this.refresh();
+ this.scrollTo( xy.x, xy.y );
+ },
- mat4.translate( nodes[i].mvMatrix, position );
- mat4.rotate( nodes[i].mvMatrix, angle, [0, 1, 0] );
- }
+ refresh: function () {
+ var itemsPerView;
- if ( imageListLength > itemCount && progress >= self._ANIMATION_END ) {
- self._firstImageNumber = ( self._firstImageNumber - direction ) % imageListLength;
- if ( self._firstImageNumber < 0 ) {
- self._firstImageNumber = imageListLength - 1;
- }
+ this._$clip.width( $(window).width() );
+ this._clipWidth = this._$clip.width();
+ this._$list.empty();
+ this._$list.append(this._items[0]);
+ this._itemWidth = $(this._items[0]).outerWidth();
+ $(this._items[0]).detach();
- self._lastImageNumber = ( self._lastImageNumber - direction ) % imageListLength;
- if ( self._lastImageNumber < 0 ) {
- self._lastImageNumber = imageListLength - 1;
- }
+ itemsPerView = this._clipWidth / this._itemWidth;
+ itemsPerView = Math.ceil( itemsPerView * 10 ) / 10;
+ this._itemsPerView = parseInt( itemsPerView, 10 );
+ while ( this._itemsPerView + 1 > this._items.length ) {
+ $.merge( this._items, $(this._items).clone() );
}
- self._drawScene();
+ this._rx = -this._itemWidth;
+ this._sx = -this._itemWidth;
+ this._setItems();
},
- _drawScene: function () {
- if ( !this._gl || !this._shaderProgram ) {
- return;
- }
-
- var self = this,
- gl = self._gl,
- shaderProgram = self._shaderProgram,
- nodes = self._nodes,
- nodesLength = nodes.length,
- i;
-
- gl.clear( gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT );
+ _startMScroll: function ( speedX, speedY ) {
+ this._stopMScroll();
- gl.bindBuffer( gl.ARRAY_BUFFER, self._positionBuffer );
- gl.vertexAttribPointer( shaderProgram.vertexPositionAttr, self._positionBuffer.itemSize, gl.FLOAT, false, 0, 0 );
+ var keepGoing = false,
+ duration = this.options.scrollDuration,
+ t = this._tracker,
+ c = this._clipWidth,
+ v = this._viewWidth;
- gl.bindBuffer( gl.ARRAY_BUFFER, self._textureCoordBuffer );
- gl.vertexAttribPointer( shaderProgram.textureCoordAttr, self._textureCoordBuffer.itemSize, gl.FLOAT, false, 0, 0 );
+ this._$clip.trigger( this.options.startEventName);
- gl.bindBuffer( gl.ARRAY_BUFFER, self._normalVectorBuffer );
- gl.vertexAttribPointer( shaderProgram.vertexNormalAttr, self._normalVectorBuffer.itemSize, gl.FLOAT, false, 0, 0 );
+ t.start( this._rx, speedX, duration, (v > c ) ? -(v - c) : 0, 0 );
+ keepGoing = !t.done();
- for ( i = 0; i < nodesLength; i += 1 ) {
- if ( nodes[i].drawable ) {
- self._drawElement( self._pMatrix, nodes[i] );
- }
+ if ( keepGoing ) {
+ this._timerID = setTimeout( this._timerCB, this._timerInterval );
+ } else {
+ this._stopMScroll();
}
+ //console.log( "startmscroll" + this._rx + "," + this._sx );
},
- _drawElement: function ( perspectiveMatrix, targetNode ) {
- var self = this,
- gl = self._gl,
- vec3 = glMatrix.vec3,
- mat3 = glMatrix.mat3,
- mat4 = glMatrix.mat4,
- shaderProgram = self._shaderProgram,
- moveMatrix = targetNode.mvMatrix,
- texture = targetNode.texture,
- meshIndexBuffer = targetNode.textureBuffer,
- meshIndexBufferItemSize = targetNode.textureBufferItemSize,
- lightPositions = self._lightsPositionStack,
- LightDir,
- normalMatrix;
-
- if ( !moveMatrix ) {
- return;
+ _stopMScroll: function () {
+ if ( this._timerID ) {
+ this._$clip.trigger( this.options.stopEventName );
+ clearTimeout( this._timerID );
}
- gl.activeTexture( gl.TEXTURE0 );
- if ( texture && texture.loaded ) {
- gl.bindTexture( gl.TEXTURE_2D, texture );
+ this._timerID = 0;
+
+ if ( this._tracker ) {
+ this._tracker.reset();
}
- gl.uniform1i( shaderProgram.sampleUniform, 0 );
+ //console.log( "stopmscroll" + this._rx + "," + this._sx );
+ },
- LightDir = vec3.create();
- vec3.normalize( lightPositions[0], LightDir );
- vec3.scale( LightDir, -8 );
- gl.uniform3fv( shaderProgram.lightDirU_first, LightDir );
+ _handleMomentumScroll: function () {
+ var keepGoing = false,
+ v = this._$view,
+ x = 0,
+ y = 0,
+ t = this._tracker;
- vec3.normalize( lightPositions[1], LightDir );
- vec3.scale( LightDir, -1 );
- gl.uniform3fv( shaderProgram.lightDirU_second, LightDir );
- gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, meshIndexBuffer );
+ if ( t ) {
+ t.update();
+ x = t.getPosition();
- gl.uniformMatrix4fv( shaderProgram.perspectiveMU, false, perspectiveMatrix );
- gl.uniformMatrix4fv( shaderProgram.transformMU, false, moveMatrix );
+ keepGoing = !t.done();
- normalMatrix = mat3.create();
- mat4.toInverseMat3( moveMatrix, normalMatrix );
- mat3.transpose( normalMatrix );
- gl.uniformMatrix3fv( shaderProgram.normalMU, false, normalMatrix );
+ }
- gl.drawElements( gl.TRIANGLES, meshIndexBufferItemSize, gl.UNSIGNED_SHORT, 0 );
+ this._setScrollPosition( x, y );
+ this._rx = x;
- // release buffer memory
- gl.bindBuffer( gl.ARRAY_BUFFER, null );
- gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, null );
+ this._$clip.trigger( this.options.updateEventName, [ { x: x, y: y } ] );
- // release texture memory
- gl.bindTexture( gl.TEXTURE_2D, null );
+ if ( keepGoing ) {
+ this._timerID = setTimeout( this._timerCB, this._timerInterval );
+ } else {
+ this._stopMScroll();
+ }
},
- // ----------------------------------------------------------
- // Animation
- // ----------------------------------------------------------
- _animate: function ( easingType, duration, direction, repeatCount, startValue, _removeCount ) {
- var self = this,
- timeNow = $.now(),
- progress,
- removeCount = 0;
-
- easingType = easingType || "linear";
- startValue = startValue || 0;
- _removeCount = _removeCount || 0;
+ _setItems: function () {
+ var i,
+ $item;
- if ( self._sumTime >= duration ) {
- self._setPosition( self._ANIMATION_END, direction );
- self._stop();
- return;
+ for ( i = -1; i < this._itemsPerView + 1; i++ ) {
+ $item = this._items[ circularNum( i, this._items.length ) ];
+ this._$list.append( $item );
}
+ setElementTransform( this._$view, this._sx + "px", 0 );
+ this._$view.width( this._itemWidth * ( this._itemsPerView + 2 ) );
+ this._viewWidth = this._$view.width();
+ },
- if ( self._startTime === 0 ) {
- self._startTime = timeNow;
- } else {
- self._sumTime = timeNow - self._startTime;
- progress = $.easing[ easingType ]( self._sumTime / duration, self._sumTime, startValue, repeatCount + 1, duration );
- removeCount = parseInt( Math.abs( progress ), 10 );
-
- if ( _removeCount !== removeCount ) {
- self._setPosition( self._ANIMATION_END, direction );
- _removeCount = removeCount;
+ _setScrollPosition: function ( x, y ) {
+ var sx = this._sx,
+ dx = x - sx,
+ di = parseInt( dx / this._itemWidth, 10 ),
+ i,
+ idx,
+ $item;
- if ( ( repeatCount - _removeCount ) >= 0 ) {
- self._animate( easingType, duration, direction, repeatCount, startValue, _removeCount );
- } else {
- self._stop();
- }
- return;
+ if ( di > 0 ) {
+ for ( i = 0; i < di; i++ ) {
+ this._$list.children().last().detach();
+ idx = -parseInt( ( sx / this._itemWidth ) + i + 3, 10 );
+ $item = this._items[ circularNum( idx, this._items.length ) ];
+ this._$list.prepend( $item );
+ //console.log( "di > 0 : " + idx );
+ }
+ } else if ( di < 0 ) {
+ for ( i = 0; i > di; i-- ) {
+ this._$list.children().first().detach();
+ idx = this._itemsPerView - parseInt( ( sx / this._itemWidth ) + i, 10 );
+ $item = this._items[ circularNum( idx, this._items.length ) ];
+ this._$list.append( $item );
+ //console.log( "di < 0 : " + idx );
}
-
- self._setPosition( progress - _removeCount, direction );
}
- self._animationID = requestAnimationFrame( function () {
- self._animate( easingType, duration, direction, repeatCount, startValue, _removeCount );
- });
+ this._sx += di * this._itemWidth;
+
+ setElementTransform( this._$view, ( x - this._sx - this._itemWidth ) + "px", 0 );
+
+ //console.log( "rx " + this._rx + "sx " + this._sx );
},
- _run: function ( direction, repeatCount, startValue ) {
- var self = this,
- repeat = repeatCount || 0,
- duration = self._DURATION_DEFAULT * ( repeat + 1 );
+ _enableTracking: function () {
+ $(document).bind( this._dragMoveEvt, this._dragMoveCB );
+ $(document).bind( this._dragStopEvt, this._dragStopCB );
+ },
- if ( self._imageList.length <= 1 ) {
- return;
- }
+ _disableTracking: function () {
+ $(document).unbind( this._dragMoveEvt, this._dragMoveCB );
+ $(document).unbind( this._dragStopEvt, this._dragStopCB );
+ },
- startValue = startValue || 0;
- duration = ( duration >= 0 ) ? duration : 0;
+ _getScrollHierarchy: function () {
+ var svh = [],
+ d;
+ this._$clip.parents( '.ui-scrollview-clip' ).each( function () {
+ d = $( this ).jqmData( 'circulaview' );
+ if ( d ) {
+ svh.unshift( d );
+ }
+ } );
+ return svh;
+ },
- if ( self._animationID ) {
- self._setPosition( self._ANIMATION_END, direction );
- self._stop();
- }
+ centerTo: function ( selector, duration ) {
+ var i,
+ newX;
- self._animate( "easeOutExpo", duration, direction, repeat, startValue );
+ for ( i = 0; i < this._items.length; i++ ) {
+ if ( $( this._items[i]).is( selector ) ) {
+ newX = -( i * this._itemWidth - this._clipWidth / 2 + this._itemWidth * 1.5 );
+ this.scrollTo( newX + this._itemWidth, 0 );
+ this.scrollTo( newX, 0, duration );
+ return;
+ }
+ }
},
- _reset: function () {
- if ( !this._canvas || !this._gl ) {
+ scrollTo: function ( x, y, duration ) {
+ this._stopMScroll();
+ if ( !duration ) {
+ this._setScrollPosition( x, y );
+ this._rx = x;
return;
}
- this._final();
- this._init();
- this.refresh();
- },
+ var self = this,
+ start = getCurrentTime(),
+ efunc = $.easing.easeOutQuad,
+ sx = this._rx,
+ sy = 0,
+ dx = x - sx,
+ dy = 0,
+ tfunc,
+ elapsed,
+ ec;
- _stop: function () {
- if ( this._animationID ) {
- cancelAnimationFrame( this._animationID );
- }
- this._animationID = 0;
+ this._rx = x;
- this._startTime = 0;
- this._sumTime = 0;
- },
+ tfunc = function () {
+ elapsed = getCurrentTime() - start;
+ if ( elapsed >= duration ) {
+ self._timerID = 0;
+ self._setScrollPosition( x, y );
+ self._$clip.trigger("scrollend");
+ } else {
+ ec = efunc( elapsed / duration, elapsed, 0, 1, duration );
+ self._setScrollPosition( sx + ( dx * ec ), sy + ( dy * ec ) );
+ self._timerID = setTimeout( tfunc, self._timerInterval );
+ }
+ };
- next: function () {
- this._run( this._DIRECTION_LEFT , 0 );
+ this._timerID = setTimeout( tfunc, this._timerInterval );
},
- prev: function () {
- this._run( this._DIRECTION_RIGHT, 0 );
+ getScrollPosition: function () {
+ return { x: -this._rx, y: 0 };
},
- refresh: function () {
- var view = this.element,
- canvas = view.find( "canvas.ui-gallery3d-canvas" );
+ _handleDragStart: function ( e, ex, ey ) {
+ $.each( this._getScrollHierarchy(), function ( i, sv ) {
+ sv._stopMScroll();
+ } );
- if ( canvas.width() !== view.width() ) {
- canvas.width( view.width() );
- }
+ this._stopMScroll();
- if ( !this._animationID ) {
- this._setPosition( 0, 0 );
+ if ( this.options.delayedClickEnabled ) {
+ this._$clickEle = $( e.target ).closest( this.options.delayedClickSelector );
}
- },
+ this._lastX = ex;
+ this._lastY = ey;
+ this._speedX = 0;
+ this._speedY = 0;
+ this._didDrag = false;
- select: function ( index ) {
- var nodes = this._nodes,
- repeat,
- i,
- imageID,
- object = null,
- target = 0,
- direction = 0;
+ this._lastMove = 0;
+ this._enableTracking();
- if ( index && this._animationID ) {
- this._stop();
- }
+ this._ox = ex;
+ this._nx = this._rx;
- for ( i in nodes ) {
- if ( nodes[i].level === 1 ) {
- object = this._imageList[ nodes[i].imageID ];
- imageID = nodes[i].imageID;
- break;
- }
+ if ( this.options.eventType == "mouse" || this.options.delayedClickEnabled ) {
+ e.preventDefault();
}
+ //console.log( "scrollstart" + this._rx + "," + this._sx );
+ e.stopPropagation();
+ },
- if ( !index ) {
- return object;
- }
+ _handleDragMove: function ( e, ex, ey ) {
+ this._lastMove = getCurrentTime();
- if ( index < 0 && index >= this._imageList.length ) {
- return;
- }
+ var dx = ex - this._lastX,
+ dy = ey - this._lastY;
- target = index - imageID;
- direction = ( target > 0 ) ? this._DIRECTION_LEFT
- : ( ( target < 0 ) ? this._DIRECTION_RIGHT : 0 );
- if ( direction ) {
- this._run( direction, Math.abs( target ) - 1 );
- }
- },
+ this._speedX = dx;
+ this._speedY = 0;
- add: function ( item, index ) {
- if ( !item ) {
- return;
- }
+ this._didDrag = true;
- if ( typeof item === "string" ) {
- item = { "src" : item };
- }
+ this._lastX = ex;
+ this._lastY = ey;
- index = index || 0;
- if ( typeof index !== "number" && index < 0
- && index >= this._imageList.length ) {
- return;
- }
+ this._mx = ex - this._ox;
- this._imageList.splice( index, 0, item );
- if ( this._gl ) {
- this._reset();
- }
+ this._setScrollPosition( this._nx + this._mx, 0 );
+
+ //console.log( "scrollmove" + this._rx + "," + this._sx );
+ return false;
},
- remove: function ( index ) {
- index = index || 0;
- if ( typeof index !== "number" && index < 0
- && index >= this._imageList.length ) {
- return;
- }
+ _handleDragStop: function ( e ) {
+ var l = this._lastMove,
+ t = getCurrentTime(),
+ doScroll = l && ( t - l ) <= this.options.moveIntervalThreshold,
+ sx = ( this._tracker && this._speedX && doScroll ) ? this._speedX : 0,
+ sy = 0;
- this._imageList.splice( index, 1 );
- if ( this._gl ) {
- this._reset();
- }
- },
+ this._rx = this._mx ? this._nx + this._mx : this._rx;
- clearThumbnailCache: function () {
- if ( !this._nodes || ( this._nodes.length <= 0 ) ) {
- return;
+ if ( sx ) {
+ this._startMScroll( sx, sy );
}
- var i, url;
- for ( i = 0; i < this._imageList.length; i += 1 ) {
- url = this._imageList[i].src;
- $.imageloader.removeThumbnail( url );
- }
- },
+ //console.log( "scrollstop" + this._rx + "," + this._sx );
- empty: function () {
- this._imageList = [];
- this._reset();
- },
+ this._disableTracking();
- length: function () {
- return this._imageList.length;
- }
- });
+ if ( !this._didDrag && this.options.delayedClickEnabled && this._$clickEle.length ) {
+ this._$clickEle
+ .trigger( "mousedown" )
+ .trigger( "mouseup" )
+ .trigger( "click" );
+ }
- $( document ).on( "pagecreate create", function ( e ) {
- $( ":jqmData(role='gallery3d')" ).gallery3d();
- }).on( "pagechange", function ( e ) {
- $( e.target ).find( ".ui-gallery3d" ).gallery3d( "refresh" );
- });
+ if ( this._didDrag ) {
+ e.preventDefault();
+ e.stopPropagation();
+ }
- $( window ).on( "resize orientationchange", function ( e ) {
- $( ".ui-page-active" ).find( ".ui-gallery3d" ).gallery3d( "refresh" );
- });
+ return this._didDrag ? false : undefined;
+ },
-} ( jQuery, document, window ) );
+ _addBehaviors: function () {
+ var self = this;
+ if ( this.options.eventType === "mouse" ) {
+ this._dragStartEvt = "mousedown";
+ this._dragStartCB = function ( e ) {
+ return self._handleDragStart( e, e.clientX, e.clientY );
+ };
+ this._dragMoveEvt = "mousemove";
+ this._dragMoveCB = function ( e ) {
+ return self._handleDragMove( e, e.clientX, e.clientY );
+ };
-/**
- @class Button
- The button widget shows a control on the screen that you can use to generate an action event when it is pressed and released. This widget is coded with standard HTML anchor and input elements and then enhanced by jQueryMobile to make it more attractive and usable on a mobile device. Buttons can be used in Tizen as described in the jQueryMobile documentation for buttons.
+ this._dragStopEvt = "mouseup";
+ this._dragStopCB = function ( e ) {
+ return self._handleDragStop( e );
+ };
- To add a button widget to the application, use the following code
+ this._$view.bind( "vclick", function (e) {
+ return !self._didDrag;
+ } );
- <div data-role="button" data-inline="true">Text Button Test</div>
- <div data-role="button" data-inline="true" data-icon="plus" data-style="circle"></div>
- <div data-role="button" data-inline="true" data-icon="plus" data-style="nobg"></div>
+ } else { //touch
+ this._dragStartEvt = "touchstart";
+ this._dragStartCB = function ( e ) {
+ var t = e.originalEvent.targetTouches[0];
+ return self._handleDragStart(e, t.pageX, t.pageY );
+ };
- The button can define callbacks for events as described in the jQueryMobile documentation for button events.<br/>
- You can use methods with the button as described in the jQueryMobile documentation for button methods.
-*/
+ this._dragMoveEvt = "touchmove";
+ this._dragMoveCB = function ( e ) {
+ var t = e.originalEvent.targetTouches[0];
+ return self._handleDragMove(e, t.pageX, t.pageY );
+ };
-/**
- @property {String} data-style
- Defines the button style. <br/> The default value is box. If the value is set to circle, a circle-shaped button is created. If the value is set to nobg, a button is created without a background.
+ this._dragStopEvt = "touchend";
+ this._dragStopCB = function ( e ) {
+ return self._handleDragStop( e );
+ };
+ }
+ this._$view.bind( this._dragStartEvt, this._dragStartCB );
+ }
+ } );
-*/
-/**
- @property {String} data-icon
- Defines an icon for a button. Tizen supports 12 icon styles: reveal, closed, opened, info, rename, call, warning, plus, minus, cancel, send, and favorite.
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $( $.mobile.circularview.prototype.options.initSelector, e.target ).circularview();
+ } );
-*/
+}( jQuery, window, document ) ); // End Component
-/*
- * jQuery Mobile Widget @VERSION
- *
- * TODO: remove unnecessary codes....
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
*
- * This software is licensed under the MIT licence (as defined by the OSI at
- * http://www.opensource.org/licenses/mit-license.php)
- *
- * ***************************************************************************
- * Copyright (C) 2011 by Intel Corporation Ltd.
- *
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
- *
+ *
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
- *
+ *
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* DEALINGS IN THE SOFTWARE.
* ***************************************************************************
*
- * Authors: Kalyan Kondapally <kalyan.kondapally@intel.com>
- */
-
-ensureNS("jQuery.mobile.tizen");
-
-(function () {
-jQuery.extend(jQuery.mobile.tizen, {
- disableSelection: function (element) {
- this.enableSelection(
- $(element).find('*').not( 'input, [type="text"], textarea' ),
- 'none'
- );
- return true;
- },
-
- enableSelection: function (element, value) {
- var val;
- switch ( value ) {
- case 'text' :
- case 'auto' :
- case 'none' :
- val = value;
- break;
- default :
- val = 'auto';
- break;
- }
- return $(element).css( {
- 'user-select': val,
- '-moz-user-select': val,
- '-webkit-user-select': val,
- '-o-user-select': val,
- '-ms-transform': val
- } );
- },
-
- disableContextMenu: function(element) {
- var self = this;
- $(element).find('*').each( function() {
- if( ( $(this).get(0).tagName !== 'INPUT' &&
- $(this).attr("type") !== 'text' ) &&
- $(this).get(0).tagName !== 'TEXTAREA' ) {
- self._disableContextMenu( this );
- }
- } );
- },
-
- _disableContextMenu: function(element) {
-
- $(element).each( function() {
- $(this).bind("contextmenu", function( event ) {
- return false;
- } );
- } );
- },
-
- enableContextMenu: function(element) {
- $(element).each( function() {
- $(this).unbind( "contextmenu" );
- } );
- },
-
- // Get document-relative mouse coordinates from a given event
- // From: http://www.quirksmode.org/js/events_properties.html#position
- documentRelativeCoordsFromEvent: function(ev) {
- var e = ev ? ev : window.event,
- client = { x: e.clientX, y: e.clientY },
- page = { x: e.pageX, y: e.pageY },
- posx = 0,
- posy = 0;
-
- // Grab useful coordinates from touch events
- if (e.type.match(/^touch/)) {
- page = {
- x: e.originalEvent.targetTouches[0].pageX,
- y: e.originalEvent.targetTouches[0].pageY
- };
- client = {
- x: e.originalEvent.targetTouches[0].clientX,
- y: e.originalEvent.targetTouches[0].clientY
- };
- }
-
- if (page.x || page.y) {
- posx = page.x;
- posy = page.y;
- }
- else
- if (client.x || client.y) {
- posx = client.x + document.body.scrollLeft + document.documentElement.scrollLeft;
- posy = client.y + document.body.scrollTop + document.documentElement.scrollTop;
- }
-
- return { x: posx, y: posy };
- },
+ * Authors: Yonghwi Park <yonghwi0324.park@samsung.com>
+ * Wonseop Kim <wonseop.kim@samsung.com>
+*/
- // TODO : offsetX, offsetY. touch events don't have offsetX and offsetY. support for touch devices.
- // check algorithm...
- targetRelativeCoordsFromEvent: function(e) {
- var coords = { x: e.offsetX, y: e.offsetY };
+/**
+ *
+ * MultiMediaView is a widget that lets the user view and handle multimedia contents.
+ * Video and audio elements are coded as standard HTML elements and enhanced by the
+ * MultiMediaview to make them attractive and usable on a mobile device.
+ *
+ * HTML Attributes:
+ * data-theme : Set a theme of widget.
+ * If this value is not defined, widget will use parent`s theme. (optional)
+ * data-controls : If this value is 'true', widget will use belonging controller.
+ * If this value is 'false', widget will use browser`s controller.
+ * Default value is 'true'.
+ * data-full-screen : Set a status that full-screen when inital start.
+ * Default value is 'false'.
+ *
+ * APIs:
+ * width( [number] )
+ * : Get or set the width of widget.
+ * The first argument is the width of widget.
+ * If no first argument is specified, will act as a getter.
+ * height( [number] )
+ * : Get or set the height of widget.
+ * The first argument is the height of widget.
+ * If no first argument is specified, will act as a getter.
+ * fullScreen( [boolean] )
+ * : Get or Set the status of full-screen.
+ * If no first argument is specified, will act as a getter.
+ *
+ * Events:
+ *
+ * N/A
+ *
+ * Examples:
+ *
+ * VIDEO :
+ * <video data-controls="true" style="width:100%;">
+ * <source src="media/oceans-clip.mp4" type="video/mp4" />
+ * Your browser does not support the video tag.
+ * </video>
+ *
+ * AUDIO :
+ * <audio data-controls="true" style="width:100%;">
+ * <source src="media/Over the horizon.mp3" type="audio/mp3" />
+ * Your browser does not support the audio tag.
+ * </audio>
+ *
+ */
+/**
+ @class MutimediaView
+ The multimedia view widget shows a player control that you can use to view and handle multimedia content. This widget uses the standard HTML video and audio elements, which have been enhanced for use on a mobile device.
- if (coords.x === undefined || isNaN(coords.x) ||
- coords.y === undefined || isNaN(coords.y)) {
- var offset = $(e.target).offset();
- //coords = documentRelativeCoordsFromEvent(e); // Old code. Must be checked again.
- coords = $.mobile.tizen.documentRelativeCoordsFromEvent(e);
- coords.x -= offset.left;
- coords.y -= offset.top;
- }
+ To add a multimedia view widget to the application, use the following code:
+
+ // Video player control
+ <video data-controls="true" style="width:100%;">
+ <source src="<VIDEO_FILE_URL>" type="video/mp4" /> Your browser does not support the video tag. </video>
+ // Audio player control
+ <audio data-controls="true" style="width:100%;"> <source src="<AUDIO_FILE_URL>" type="audio/mp3" /> Your browser does not support the audio tag.
+ </audio>
+*/
+/**
+ @property {Boolean} data-control
+ Sets the controls for the widget.
+ The default value is true. If the value is set to true, the widget uses its own player controls. If the value is set to false, the widget uses the browser's player controls.
+*/
+/**
+ @property {Boolean} data-full-screen
+ Defines whether the widget opens in the fullscreen view mode.
+ The default value is false.
+*/
+/**
+ @property {String} data-theme
+ Sets the widget theme.
+ If the value is not set, the parent control's theme is used
+*/
+/**
+ @method width
+ The width method is used to get (if no value is defined) or set the multimedia view widget width:
+ <video>
+ <source src="test.mp4" type="video/mp4" />
+ </video>
+ $(".selector").multimediaview("width", [value]);
+*/
+/**
+ @method height
+ The height method is used to get (if no value is defined) or set the multimedia view widget height:
+ <video>
+ <source src="test.mp4" type="video/mp4" />
+ </video>
+ $(".selector").multimediaview("height", [value]);
+*/
+/**
+ @method fullScreen
+ The fullScreen method is used to get (if no value is defined) or set the full-screen mode of the multimedia view widget. If the value is true, the full-screen mode is used; otherwise the multimedia view widget runs in the normal mode.
- return coords;
- }
-});
+ <video>
+ <source src="test.mp4" type="video/mp4" />
+ </video>
+ $(".selector").multimediaview("fullScreen", [value]);
+*/
+( function ( $, document, window, undefined ) {
+ $.widget( "tizen.multimediaview", $.mobile.widget, {
+ options: {
+ theme: null,
+ controls: true,
+ fullScreen: false,
+ initSelector: "video, audio"
+ },
-})();
+ _create: function () {
+ var self = this,
+ view = self.element,
+ viewElement = view[0],
+ isVideo = ( viewElement.nodeName === "VIDEO" ),
+ option = self.options,
+ parentTheme = $.mobile.getInheritedTheme( view, "s" ),
+ theme = option.theme || parentTheme,
+ width = viewElement.style.getPropertyValue( "width" ) || "",
+ wrap = $( "<div class='ui-multimediaview-wrap ui-multimediaview-" + theme + "'>" ),
+ control = null;
+ $.extend( this, {
+ role: null,
+ controlTimer: null,
+ isVolumeHide: true,
+ backupView: null,
+ _reserveVolume: -1,
+ _isVideo: isVideo
+ });
+ view.addClass( "ui-multimediaview" );
+ control = self._createControl();
+ control.hide();
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Author: Jinhyuk Jun <jinhyuk.jun@samsung.com>
- */
+ control.find( ".ui-button" ).each( function ( index ) {
+ $( this ).buttonMarkup( { corners: true, theme: theme, shadow: true } );
+ });
-(function ( $, undefined ) {
+ view.wrap( wrap ).after( control );
- $.widget( "mobile.pagelayout", $.mobile.widget, {
- options: {
- visibleOnPageShow: true,
- disablePageZoom: true,
- transition: "slide", //can be none, fade, slide (slide maps to slideup or slidedown)
- fullscreen: false,
- tapToggle: true,
- tapToggleBlacklist: "a, input, select, textarea, .ui-header-fixed, .ui-footer-fixed",
- hideDuringFocus: "input, textarea, select",
- updatePagePadding: true,
- // Browser detection! Weeee, here we go...
- // Unfortunately, position:fixed is costly, not to mention probably impossible, to feature-detect accurately.
- // Some tests exist, but they currently return false results in critical devices and browsers, which could lead to a broken experience.
- // Testing fixed positioning is also pretty obtrusive to page load, requiring injected elements and scrolling the window
- // The following function serves to rule out some popular browsers with known fixed-positioning issues
- // This is a plugin option like any other, so feel free to improve or overwrite it
- supportBlacklist: function () {
- var w = window,
- ua = navigator.userAgent,
- platform = navigator.platform,
- // Rendering engine is Webkit, and capture major version
- wkmatch = ua.match( /AppleWebKit\/([0-9]+)/ ),
- wkversion = !!wkmatch && wkmatch[ 1 ],
- ffmatch = ua.match( /Fennec\/([0-9]+)/ ),
- ffversion = !!ffmatch && ffmatch[ 1 ],
- operammobilematch = ua.match( /Opera Mobi\/([0-9]+)/ ),
- omversion = !!operammobilematch && operammobilematch[ 1 ];
+ if ( isVideo ) {
+ control.addClass( "ui-multimediaview-video" );
+ } else {
+ self.width( width );
+ self.options.fullScreen = false;
+ }
- if (
- // iOS 4.3 and older : Platform is iPhone/Pad/Touch and Webkit version is less than 534 (ios5)
- ( ( platform.indexOf( "iPhone" ) > -1 || platform.indexOf( "iPad" ) > -1 || platform.indexOf( "iPod" ) > -1 ) && wkversion && wkversion < 534 ) ||
- // Opera Mini
- ( w.operamini && ({}).toString.call( w.operamini ) === "[object OperaMini]" ) ||
- ( operammobilematch && omversion < 7458 ) ||
- //Android lte 2.1: Platform is Android and Webkit version is less than 533 (Android 2.2)
- ( ua.indexOf( "Android" ) > -1 && wkversion && wkversion < 533 ) ||
- // Firefox Mobile before 6.0 -
- ( ffversion && ffversion < 6 ) ||
- // WebOS less than 3
- ( window.palmGetResource !== undefined && wkversion && wkversion < 534 ) ||
- // MeeGo
- ( ua.indexOf( "MeeGo" ) > -1 && ua.indexOf( "NokiaBrowser/8.5.0" ) > -1 )
- ) {
- return true;
- }
+ if ( option.controls && view.attr( "controls" ) ) {
+ view.removeAttr( "controls" );
+ }
- return false;
- },
- initSelector: ":jqmData(role='content')"
+ self._addEvent();
},
- _create: function () {
+ _resize: function () {
+ this._resizeFullscreen( this.options.fullScreen );
+ this._resizeControl();
+ this._updateSeekBar();
+ this._updateVolumeState();
+ },
+ _resizeControl: function () {
var self = this,
- o = self.options,
- $el = self.element;
+ view = self.element,
+ viewElement = view[0],
+ isVideo = self._isVideo,
+ wrap = view.parent( ".ui-multimediaview-wrap" ),
+ control = wrap.find( ".ui-multimediaview-control" ),
+ buttons = control.find( ".ui-button" ),
+ playpauseButton = control.find( ".ui-playpausebutton" ),
+ seekBar = control.find( ".ui-seekbar" ),
+ durationLabel = control.find( ".ui-durationlabel" ),
+ timestampLabel = control.find( ".ui-timestamplabel" ),
+ volumeControl = control.find( ".ui-volumecontrol" ),
+ volumeBar = volumeControl.find( ".ui-volumebar" ),
+ width = ( isVideo ? view.width() : wrap.width() ),
+ height = ( isVideo ? view.height() : control.height() ),
+ offset = view.offset(),
+ controlHeight = control.height(),
+ availableWidth = 0,
+ controlOffset = null;
- // Feature detecting support for
- if ( o.supportBlacklist() ) {
- self.destroy();
- return;
+ if ( control ) {
+ if ( isVideo ) {
+ controlOffset = control.offset();
+ controlOffset.left = offset.left;
+ controlOffset.top = offset.top + height - controlHeight;
+ control.offset( controlOffset );
+ }
+ control.width( width );
}
- self._addFixedClass();
- self._addTransitionClass();
- self._bindPageEvents();
-
- // only content
- self._bindContentControlEvents();
-
- // Store back-button, to show again
- self._backBtnQueue = [];
- },
+ if ( seekBar ) {
+ availableWidth = control.width() - ( buttons.outerWidth( true ) * buttons.length );
+ availableWidth -= ( parseInt( buttons.eq( 0 ).css( "margin-left" ), 10 ) + parseInt( buttons.eq( 0 ).css( "margin-right" ), 10 ) ) * buttons.length;
+ if ( !self.isVolumeHide ) {
+ availableWidth -= volumeControl.outerWidth( true );
+ }
+ seekBar.width( availableWidth );
+ }
- /* add minimum fixed css style to bar(header/footer) and content
- * it need to update when core source modified(jquery.mobile.page.section.js)
- * modified from core source cuz initSelector different */
- _addFixedClass: function () {
- var self = this,
- o = self.options,
- $el = self.element,
- $elHeader = $el.siblings( ":jqmData(role='header')" ),
- $elFooter = $el.siblings( ":jqmData(role='footer')" ),
- $elPage = $el.closest(".ui-page");
+ if ( durationLabel && !isNaN( viewElement.duration ) ) {
+ durationLabel.find( "p" ).text( self._convertTimeFormat( viewElement.duration ) );
+ }
- $elHeader.addClass( "ui-header-fixed" );
- $elFooter.addClass( "ui-footer-fixed" );
+ if ( viewElement.autoplay && viewElement.paused === false ) {
+ playpauseButton.removeClass( "ui-play-icon" ).addClass( "ui-pause-icon" );
+ }
- // "fullscreen" overlay positioning
- if ( o.fullscreen ) {
- $elHeader.addClass( "ui-header-fullscreen" );
- $elFooter.addClass( "ui-footer-fullscreen" );
- $elPage
- .addClass( "ui-page-header-fullscreen" )
- .addClass( "ui-page-footer-fullscreen" );
+ if ( seekBar.width() < ( volumeBar.width() + timestampLabel.width() + durationLabel.width() ) ) {
+ durationLabel.hide();
} else {
- // If not fullscreen, add class to page to set top or bottom padding
- $elPage.addClass( "ui-page-header-fixed" )
- .addClass( "ui-page-footer-fixed" );
+ durationLabel.show();
}
},
- /* original core source(jquery.mobile.fixedToolbar.js)
- * never changed */
- _addTransitionClass: function () {
- var tclass = this.options.transition;
+ _resizeFullscreen: function ( isFullscreen ) {
+ if ( !this._isVideo ) {
+ return;
+ }
+
+ var self = this,
+ view = self.element,
+ viewElement = view[0],
+ wrap = view.parent( ".ui-multimediaview-wrap" ),
+ control = wrap.find( ".ui-multimediaview-control" ),
+ fullscreenButton = control.find( ".ui-fullscreenbutton" ),
+ currentPage = $( ".ui-page-active" ),
+ playpauseButton = control.find( ".ui-playpausebutton" ),
+ timestampLabel = control.find( ".ui-timestamplabel" ),
+ seekBar = control.find( ".ui-seekbar" ),
+ durationBar = seekBar.find( ".ui-duration" ),
+ currenttimeBar = seekBar.find( ".ui-currenttime" ),
+ body = $( "body" )[0],
+ header = currentPage.children( ".ui-header" ),
+ footer = currentPage.children( ".ui-footer" ),
+ docWidth = 0,
+ docHeight = 0;
- if ( tclass && tclass !== "none" ) {
- // use appropriate slide for header or footer
- if ( tclass === "slide" ) {
- tclass = this.element.is( ".ui-header" ) ? "slidedown" : "slideup";
+ if ( isFullscreen ) {
+ if ( !self.backupView ) {
+ self.backupView = {
+ width: viewElement.style.getPropertyValue( "width" ) || "",
+ height: viewElement.style.getPropertyValue( "height" ) || "",
+ position: view.css( "position" ),
+ zindex: view.css( "z-index" ),
+ wrapHeight: wrap[0].style.getPropertyValue( "height" ) || ""
+ };
}
+ docWidth = body.clientWidth;
+ docHeight = body.clientHeight - 1;
- this.element.addClass( tclass );
- }
- },
-
-
- /* Set default page positon
- * 1. add title style to header
- * 2. Set default header/footer position */
- setHeaderFooter: function ( thisPage ) {
- var $elPage = $( thisPage ),
- $elHeader = $elPage.find( ":jqmData(role='header')" ).length ? $elPage.find( ":jqmData(role='header')") : $elPage.siblings( ":jqmData(role='header')"),
- $elContent = $elPage.find( ".ui-content" ),
- $elFooter = $elPage.find( ":jqmData(role='footer')" ),
- $elFooterGroup = $elFooter.find( ":jqmData(role='fieldcontain')" ),
- $elFooterControlGroup = $elFooter.find( ".ui-controlgroup" );
+ header.hide();
+ footer.hide();
+ view.parents().each( function ( e ) {
+ var element = $( this );
+ element.addClass( "ui-fullscreen-parents" )
+ .siblings()
+ .addClass( "ui-multimediaview-siblings-off" );
+ });
+ fullscreenButton.removeClass( "ui-fullscreen-on" ).addClass( "ui-fullscreen-off" );
- // divide content mode scrollview and non-scrollview
- if ( !$elPage.is( ".ui-dialog" ) ) {
- if ( $elHeader.jqmData("position") == "fixed" || ( $.support.scrollview && $.tizen.frameworkData.theme.match(/tizen/) ) ) {
- $elHeader
- .css( "position", "fixed" )
- .css( "top", "0px" );
- } else if ( !$.support.scrollview && $elHeader.jqmData("position") != "fixed" ) {
- $elHeader.css( "position", "relative" );
+ wrap.height( docHeight );
+ view.width( docWidth ).height( docHeight );
+ } else {
+ if ( !self.backupView ) {
+ return;
}
- }
- /* set Title style */
- if ( $elHeader.find("span.ui-title-text-sub").length ) {
- $elHeader.addClass( "ui-title-multiline");
- }
+ header.show();
+ footer.show();
+ view.parents().each( function ( e ) {
+ var element = $( this );
+ element.removeClass( "ui-fullscreen-parents" )
+ .siblings()
+ .removeClass( "ui-multimediaview-siblings-off" );
+ });
- if ( $elFooterGroup.find( "div" ).is( ".ui-controlgroup-label" ) ) {
- $elFooterGroup.find( "div.ui-controlgroup-label" ).remove();
- }
+ fullscreenButton.removeClass( "ui-fullscreen-off" ).addClass( "ui-fullscreen-on" );
- if ( $elFooterControlGroup.length ) {
- var anchorPer = 100 / $elFooterControlGroup.find( "a" ).length;
- $elFooterControlGroup.find( "a" ).each( function ( i ) {
- $elFooterControlGroup.find( "a" ).eq( i ).width( anchorPer + "%" );
+ wrap.css( "height", self.backupView.wrapHeight );
+ view.css( {
+ "width": self.backupView.width,
+ "height": self.backupView.height,
+ "position": self.backupView.position,
+ "z-index": self.backupView.zindex
});
+ self.backupView = null;
+
+ $( window ).trigger( "throttledresize" );
}
},
- _bindPageEvents: function () {
+ _addEvent: function () {
var self = this,
- o = self.options,
- $el = self.element,
- $elCurrentFooter;
+ view = self.element,
+ option = self.options,
+ viewElement = view[0],
+ isVideo = self._isVideo,
+ control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
+ playpauseButton = control.find( ".ui-playpausebutton" ),
+ timestampLabel = control.find( ".ui-timestamplabel" ),
+ durationLabel = control.find( ".ui-durationlabel" ),
+ volumeButton = control.find( ".ui-volumebutton" ),
+ volumeControl = control.find( ".ui-volumecontrol" ),
+ volumeBar = volumeControl.find( ".ui-volumebar" ),
+ volumeGuide = volumeControl.find( ".ui-guide" ),
+ volumeHandle = volumeControl.find( ".ui-handle" ),
+ fullscreenButton = control.find( ".ui-fullscreenbutton" ),
+ seekBar = control.find( ".ui-seekbar" ),
+ durationBar = seekBar.find( ".ui-duration" ),
+ currenttimeBar = seekBar.find( ".ui-currenttime" ),
+ $document = $( document );
- //page event bindings
- // Fixed toolbars require page zoom to be disabled, otherwise usability issues crop up
- // This method is meant to disable zoom while a fixed-positioned toolbar page is visible
- $el.closest( ".ui-page" )
- .bind( "pagebeforeshow", function ( event ) {
- var thisPage = this;
- if ( o.disablePageZoom ) {
- $.mobile.zoom.disable( true );
- }
- if ( !o.visibleOnPageShow ) {
- self.hide( true );
- }
- self.setHeaderFooter( thisPage );
- self._setContentMinHeight( thisPage );
- } )
- .bind( "webkitAnimationStart animationstart updatelayout", function ( e, data ) {
- var thisPage = this;
- if ( o.updatePagePadding ) {
- self.updatePagePadding(thisPage);
- self.updatePageLayout( thisPage, data);
- }
- })
+ view.bind( "loadedmetadata.multimediaview", function ( e ) {
+ if ( !isNaN( viewElement.duration ) ) {
+ durationLabel.find( "p" ).text( self._convertTimeFormat( viewElement.duration ) );
+ }
+ self._resize();
+ }).bind( "timeupdate.multimediaview", function ( e ) {
+ self._updateSeekBar();
+ }).bind( "play.multimediaview", function ( e ) {
+ playpauseButton.removeClass( "ui-play-icon" ).addClass( "ui-pause-icon" );
+ }).bind( "pause.multimediaview", function ( e ) {
+ playpauseButton.removeClass( "ui-pause-icon" ).addClass( "ui-play-icon" );
+ }).bind( "ended.multimediaview", function ( e ) {
+ if ( typeof viewElement.loop == "undefined" || viewElement.loop === "" ) {
+ self.stop();
+ }
+ }).bind( "volumechange.multimediaview", function ( e ) {
+ if ( viewElement.muted && viewElement.volume > 0.1 ) {
+ volumeButton.removeClass( "ui-volume-icon" ).addClass( "ui-mute-icon" );
+ self._reserveVolume = viewElement.volume;
+ viewElement.volume = 0;
+ } else if ( self._reserveVolume !== -1 && !viewElement.muted ) {
+ volumeButton.removeClass( "ui-mute-icon" ).addClass( "ui-volume-icon" );
+ viewElement.volume = self._reserveVolume;
+ self._reserveVolume = -1;
+ } else if ( viewElement.volume < 0.1 ) {
+ volumeButton.removeClass( "ui-volume-icon" ).addClass( "ui-mute-icon" );
+ } else {
+ volumeButton.removeClass( "ui-mute-icon" ).addClass( "ui-volume-icon" );
+ }
- .bind( "pageshow", function ( event ) {
- var thisPage = this;
- self._setContentMinHeight( thisPage );
- self.updatePagePadding( thisPage );
- self._updateHeaderArea( thisPage );
- if ( o.updatePagePadding ) {
- $( window ).bind( "throttledresize." + self.widgetName, function () {
- self.updatePagePadding(thisPage);
+ if ( !self.isVolumeHide ) {
+ self._updateVolumeState();
+ }
+ }).bind( "durationchange.multimediaview", function ( e ) {
+ if ( !isNaN( viewElement.duration ) ) {
+ durationLabel.find( "p" ).text( self._convertTimeFormat( viewElement.duration ) );
+ }
+ self._resize();
+ }).bind( "click.multimediaview", function ( e ) {
+ if ( !self.options.controls ) {
+ return;
+ }
- self.updatePageLayout( thisPage, false);
- self._updateHeaderArea( thisPage );
- self._setContentMinHeight( thisPage );
- });
- }
- })
+ control.fadeToggle( "fast" );
+ self._resize();
+ }).bind( "multimediaviewinit", function ( e ) {
+ if ( option.controls ) {
+ control.show();
+ }
+ self._resize();
+ });
- .bind( "pagebeforehide", function ( e, ui ) {
- if ( o.disablePageZoom ) {
- $.mobile.zoom.enable( true );
- }
- if ( o.updatePagePadding ) {
- $( window ).unbind( "throttledresize." + self.widgetName );
- }
- });
+ playpauseButton.bind( "click.multimediaview", function () {
+ self._endTimer();
- window.addEventListener( "softkeyboardchange", function ( e ) {
- var $elDownBtn = $( "<div class='ui-btn-footer-down'></div>" ),
- $elPage = $( ".ui-page-active" ),
- backBtn,
- backBtnPosition = "footer";
+ if ( viewElement.paused ) {
+ viewElement.play();
+ } else {
+ viewElement.pause();
+ }
- if ( $elPage.data( "addBackBtn" ) ) {
- $elPage.data( "addBackBtn" ) == "header" ? backBtnPosition = "header" : backBtnPosition = "footer";
+ if ( isVideo ) {
+ self._startTimer();
+ }
+ });
- if ( e.state == "on" ) {
- if ( !$elPage.find( ".ui-" + backBtnPosition + " .ui-btn-footer-down" ).length ) {
- $elDownBtn.buttonMarkup( { icon: "down" } ).appendTo( $elPage.find( ".ui-" + backBtnPosition ) );
- }
+ fullscreenButton.bind( "click.multimediaview", function ( e ) {
+ e.preventDefault();
+ self.fullScreen( !self.options.fullScreen );
+ self._resize();
+ self._endTimer();
+ e.stopPropagation();
+ });
- // N_SE-32900: If an app moves a page when the pop is shown, the .ui-page-active page
- // is changed.
- // In this case, the '.ui-page-active .ui-btn-back' selector indicates a
- // new page's one, and the old page's .ui-btn-back button is still hidden.
- // So, the current back button is remembered to be shown at the
- // softkeyboardchange.off event.
- backBtn = $( ".ui-page-active .ui-btn-back" );
- backBtn.hide();
- self._backBtnQueue.push( backBtn ); // Store hidden backBtn
- } else if ( e.state == "off" ) {
- self._backBtnQueue.forEach( function ( b ) {
- b.show(); // Show each backBtn,
- } );
- self._backBtnQueue.length = 0; // and clear queue.
+ seekBar.bind( "vmousedown.multimediaview", function ( e ) {
+ var x = e.clientX,
+ duration = viewElement.duration,
+ durationOffset = durationBar.offset(),
+ durationWidth = durationBar.width(),
+ timerate = ( x - durationOffset.left ) / durationWidth,
+ time = duration * timerate;
+
+ if ( !viewElement.played.length ) {
+ return;
+ }
+
+ viewElement.currentTime = time;
+
+ self._endTimer();
- $( ".ui-btn-footer-down" ).remove();
- }
- }
+ e.preventDefault();
+
+ $document.bind( "vmousemove.multimediaview", function ( e ) {
+ var x = e.clientX,
+ timerate = ( x - durationOffset.left ) / durationWidth;
+
+ viewElement.currentTime = duration * timerate;
+ e.preventDefault();
+ }).bind( "vmouseup.multimediaview", function () {
+ $document.unbind( "vmousemove.multimediaview vmouseup.multimediaview" );
+ if ( viewElement.paused ) {
+ viewElement.pause();
+ } else {
+ viewElement.play();
+ }
+ });
});
- },
- _bindContentControlEvents: function () {
- var self = this,
- o = self.options,
- $el = self.element;
+ volumeButton.bind( "click.multimediaview", function () {
+ if ( self.isVolumeHide ) {
+ var view = self.element,
+ volume = viewElement.volume;
- $el.closest( ".ui-page" )
- .bind( "pagebeforeshow", function ( event ) {
+ self.isVolumeHide = false;
+ volumeControl.fadeIn( "fast", function () {
+ self._updateVolumeState();
+ self._updateSeekBar();
+ });
+ self._resize();
+ } else {
+ self.isVolumeHide = true;
+ volumeControl.fadeOut( "fast", function () {
+ self._resize();
+ });
+ }
+ });
- });
- },
+ volumeBar.bind( "vmousedown.multimediaview", function ( e ) {
+ var baseX = e.clientX,
+ volumeGuideLeft = volumeGuide.offset().left,
+ volumeGuideWidth = volumeGuide.width(),
+ volumeBase = volumeGuideLeft + volumeGuideWidth,
+ handlerOffset = volumeHandle.offset(),
+ volumerate = ( baseX - volumeGuideLeft ) / volumeGuideWidth,
+ currentVolume = ( baseX - volumeGuideLeft ) / volumeGuideWidth;
- _setContentMinHeight : function ( thisPage ) {
- var $elPage = $( thisPage ),
- $elHeader = $elPage.find( ":jqmData(role='header')" ),
- $elFooter = $elPage.find( ":jqmData(role='footer')" ),
- $elContent = $elPage.find( ":jqmData(role='content')" ),
- resultMinHeight,
- dpr = 1,
- layoutInnerHeight = window.innerHeight;
+ self._endTimer();
+ self._setVolume( currentVolume.toFixed( 2 ) );
- if ( !$.support.scrollview || ($.support.scrollview && $elContent.jqmData("scroll") === "none") ) {
- dpr = window.outerWidth / window.innerWidth;
- layoutInnerHeight = Math.floor( window.outerHeight / dpr );
- } else {
- layoutInnerHeight = window.innerHeight;
- }
+ e.preventDefault();
- resultMinHeight = layoutInnerHeight - $elHeader.height() - $elFooter.height();
+ $document.bind( "vmousemove.multimediaview", function ( e ) {
+ var currentX = e.clientX,
+ currentVolume = ( currentX - volumeGuideLeft ) / volumeGuideWidth;
- if ( $.support.scrollview && $elContent.jqmData("scroll") !== "none" ) {
- $elContent.css( "min-height", resultMinHeight - parseFloat( $elContent.css("padding-top") ) - parseFloat( $elContent.css("padding-bottom") ) + "px" );
- $elContent.children( ".ui-scrollview-view" ).css( "min-height", $elContent.css( "min-height" ) );
- }
+ self._setVolume( currentVolume.toFixed( 2 ) );
+
+ e.preventDefault();
+ }).bind( "vmouseup.multimediaview", function () {
+ $document.unbind( "vmousemove.multimediaview vmouseup.multimediaview" );
+ });
+ });
},
- _updateHeaderArea : function ( thisPage ) {
- var $elPage = $( thisPage ),
- $elHeader = $elPage.find( ":jqmData(role='header')" ).length ? $elPage.find( ":jqmData(role='header')") : $elPage.siblings( ":jqmData(role='header')"),
- headerBtnNum = $elHeader.children("a").length,
- headerSrcNum = $elHeader.children("img").length;
+ _removeEvent: function () {
+ var view = this.element,
+ control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
+ playpauseButton = control.find( ".ui-playpausebutton" ),
+ fullscreenButton = control.find( ".ui-fullscreenbutton" ),
+ seekBar = control.find( ".ui-seekbar" ),
+ volumeControl = control.find( ".ui-volumecontrol" ),
+ volumeBar = volumeControl.find( ".ui-volumebar" ),
+ volumeHandle = volumeControl.find( ".ui-handle" );
- if ( !$elPage.is( ".ui-dialog" ) ) {
- $elHeader.find( "h1" ).css( "width", window.innerWidth - parseInt( $elHeader.find( "h1" ).css( "margin-left" ), 10 ) * 2 - $elHeader.children( "a" ).width() * headerBtnNum - $elHeader.children( "a" ).width() / 4 - $elHeader.children( "img" ).width() * headerSrcNum * 4 );
- }
- /* add half width for default space between text and button, and img tag area is too narrow, so multiply three for img width*/
+ view.unbind( ".multimediaview" );
+ playpauseButton.unbind( ".multimediaview" );
+ fullscreenButton.unbind( ".multimediaview" );
+ seekBar.unbind( ".multimediaview" );
+ volumeBar.unbind( ".multimediaview" );
+ volumeHandle.unbind( ".multimediaview" );
},
- _visible: true,
+ _createControl: function () {
+ var view = this.element,
+ viewElement = view[0],
+ control = $( "<span></span>" ).addClass( "ui-multimediaview-control" ),
+ playpauseButton = $( "<span></span>" ).addClass( "ui-playpausebutton ui-button ui-play-icon" ),
+ seekBar = $( "<span></span>" ).addClass( "ui-seekbar ui-multimediaview-bar" ),
+ timestampLabel = $( "<span><p>00:00:00</p></span>" ).addClass( "ui-timestamplabel" ),
+ durationLabel = $( "<span><p>00:00:00</p></span>" ).addClass( "ui-durationlabel" ),
+ volumeButton = $( "<span></span>" ).addClass( "ui-volumebutton ui-button" ),
+ volumeControl = $( "<span></span>" ).addClass( "ui-volumecontrol" ),
+ volumeBar = $( "<div></div>" ).addClass( "ui-volumebar ui-multimediaview-bar" ),
+ volumeGuide = $( "<span></span>" ).addClass( "ui-guide ui-multimediaview-bar-bg" ),
+ volumeValue = $( "<span></span>" ).addClass( "ui-value ui-multimediaview-bar-highlight" ),
+ volumeHandle = $( "<span></span>" ).addClass( "ui-handle" ),
+ fullscreenButton = $( "<span></span>" ).addClass( "ui-fullscreenbutton ui-button" ),
+ durationBar = $( "<span></span>" ).addClass( "ui-duration ui-multimediaview-bar-bg" ),
+ currenttimeBar = $( "<span></span>" ).addClass( "ui-currenttime ui-multimediaview-bar-highlight" );
- // This will set the content element's top or bottom padding equal to the toolbar's height
- updatePagePadding: function ( tbPage ) {
- var $el = this.element,
- header = $el.siblings( ".ui-header" ).length,
- footer = $el.siblings( ".ui-footer" ).length;
+ seekBar.append( durationBar ).append( currenttimeBar ).append( durationLabel ).append( timestampLabel );
- // This behavior only applies to "fixed", not "fullscreen"
- if ( this.options.fullscreen ) {
- return;
- }
+ volumeButton.addClass( viewElement.muted ? "ui-mute-icon" : "ui-volume-icon" );
+ volumeBar.append( volumeGuide ).append( volumeValue ).append( volumeHandle );
+ volumeControl.append( volumeBar );
- tbPage = tbPage || $el.closest( ".ui-page" );
+ control.append( playpauseButton ).append( seekBar ).append( volumeControl ).append( volumeButton );
- if ( $el.siblings( ".ui-header" ).jqmData("position") == "fixed" || ($.support.scrollview && $el.jqmData("scroll") !== "none" )) {
- $( tbPage ).css( "padding-top", ( header ? $el.siblings( ".ui-header" ).outerHeight() : 0 ) );
+ if ( this._isVideo ) {
+ $( fullscreenButton ).addClass( "ui-fullscreen-on" );
+ control.append( fullscreenButton );
}
- $( tbPage ).css( "padding-bottom", ( footer ? $el.siblings( ".ui-footer" ).outerHeight() : 0 ) );
+ volumeControl.hide();
+
+ return control;
},
- /* 1. Calculate and update content height */
- updatePageLayout: function ( thisPage, receiveType ) {
- var $elFooter,
- $elPage = $( thisPage ),
- $elHeader = $elPage.find( ":jqmData(role='header')" ),
- $elContent = $elPage.find( ":jqmData(role='content')" ),
- resultContentHeight = 0,
- resultFooterHeight = 0,
- resultHeaderHeight = 0,
- layoutInnerHeight = window.innerHeight,
- dpr = 1;
+ _startTimer: function ( duration ) {
+ this._endTimer();
- if ( $elPage.length ) {
- $elFooter = $elPage.find( ":jqmData(role='footer')" );
- } else {
- $elFooter = $( document ).find( ":jqmData(role='footer')" ).eq( 0 );
+ if ( !duration ) {
+ duration = 3000;
}
- // calculate footer height
- resultFooterHeight = ( $elFooter.css( "display" ) == "none" || $elFooter.length == 0 ) ? 0 : $elFooter.height();
- resultHeaderHeight = ( $elHeader.css( "display" ) == "none" || $elHeader.length == 0 ) ? 0 : $elHeader.height();
+ var self = this,
+ view = self.element,
+ control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
+ volumeControl = control.find( ".ui-volumecontrol" );
- if (resultFooterHeight != 0 ) {
- $elFooter.css( "bottom", 0 );
+ self.controlTimer = setTimeout( function () {
+ self.isVolumeHide = true;
+ self.controlTimer = null;
+ volumeControl.hide();
+ control.fadeOut( "fast" );
+ }, duration );
+ },
+
+ _endTimer: function () {
+ if ( this.controlTimer ) {
+ clearTimeout( this.controlTimer );
+ this.controlTimer = null;
}
+ },
- if ( !$.support.scrollview || ($.support.scrollview && $elContent.jqmData("scroll") === "none") ) {
- dpr = window.outerWidth / window.innerWidth;
- layoutInnerHeight = Math.floor( window.outerHeight / dpr );
- } else {
- layoutInnerHeight = window.innerHeight;
+ _convertTimeFormat: function ( systime ) {
+ if ( !$.isNumeric( systime ) ) {
+ return "Playback Error";
}
- resultContentHeight = layoutInnerHeight - resultFooterHeight - resultHeaderHeight;
+ var ss = parseInt( systime % 60, 10 ).toString(),
+ mm = parseInt( ( systime / 60 ) % 60, 10 ).toString(),
+ hh = parseInt( systime / 3600, 10 ).toString(),
+ time = ( ( hh.length < 2 ) ? "0" + hh : hh ) + ":" +
+ ( ( mm.length < 2 ) ? "0" + mm : mm ) + ":" +
+ ( ( ss.length < 2 ) ? "0" + ss : ss );
- if ( $.support.scrollview && $elContent.jqmData("scroll") !== "none" ) {
- $elContent.height( resultContentHeight -
- parseFloat( $elContent.css("padding-top") ) -
- parseFloat( $elContent.css("padding-bottom") ) );
- }
+ return time;
+ },
- // External call page( "refresh") - in case title changed
- if ( receiveType ) {
- $elPage
- .css( "min-height", resultContentHeight )
- .css( "padding-top", resultHeaderHeight )
- .css( "padding-bottom", resultFooterHeight );
+ _updateSeekBar: function ( currenttime ) {
+ var view = this.element,
+ viewElement = view[0],
+ duration = viewElement.duration,
+ control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
+ seekBar = control.find( ".ui-seekbar" ),
+ durationBar = seekBar.find( ".ui-duration" ),
+ currenttimeBar = seekBar.find( ".ui-currenttime" ),
+ timestampLabel = control.find( ".ui-timestamplabel" ),
+ durationOffset = durationBar.offset(),
+ durationWidth = durationBar.width(),
+ durationHeight = durationBar.height(),
+ timebarWidth = 0;
+
+ if ( typeof currenttime === "undefined" ) {
+ currenttime = viewElement.currentTime;
}
+ timebarWidth = parseInt( currenttime / duration * durationWidth, 10 );
+ durationBar.offset( durationOffset );
+ currenttimeBar.offset( durationOffset ).width( timebarWidth );
+ timestampLabel.find( "p" ).text( this._convertTimeFormat( currenttime ) );
},
- show: function ( notransition ) {
- /* blank function: deprecated */
+ _updateVolumeState: function () {
+ var view = this.element,
+ control = view.parent( ".ui-multimediaview-wrap" ).find( ".ui-multimediaview-control" ),
+ volumeControl = control.find( ".ui-volumecontrol" ),
+ volumeButton = control.find( ".ui-volumebutton" ),
+ volumeBar = volumeControl.find( ".ui-volumebar" ),
+ volumeGuide = volumeControl.find( ".ui-guide" ),
+ volumeValue = volumeControl.find( ".ui-value" ),
+ volumeHandle = volumeControl.find( ".ui-handle" ),
+ handlerWidth = volumeHandle.width(),
+ handlerHeight = volumeHandle.height(),
+ volumeGuideHeight = volumeGuide.height(),
+ volumeGuideWidth = volumeGuide.width(),
+ volumeGuideTop = 0,
+ volumeGuideLeft = 0,
+ volumeBase = 0,
+ handlerOffset = null,
+ volume = view[0].volume;
+
+ volumeGuideTop = parseInt( volumeGuide.offset().top, 10 );
+ volumeGuideLeft = parseInt( volumeGuide.offset().left, 10 );
+ volumeBase = volumeGuideLeft;
+ handlerOffset = volumeHandle.offset();
+ handlerOffset.top = volumeGuideTop - parseInt( ( handlerHeight - volumeGuideHeight ) / 2, 10 );
+ handlerOffset.left = volumeBase + parseInt( volumeGuideWidth * volume, 10 ) - parseInt( handlerWidth / 2, 10 );
+ volumeHandle.offset( handlerOffset );
+ volumeValue.offset( volumeGuide.offset() ).width( parseInt( volumeGuideWidth * ( volume ), 10 ) );
},
- hide: function ( notransition ) {
- /* blank function: deprecated */
- },
+ _setVolume: function ( value ) {
+ var viewElement = this.element[0];
- toggle: function () {
- this[ this._visible ? "hide" : "show" ]();
- },
+ if ( value < 0.0 || value > 1.0 ) {
+ return;
+ }
- destroy: function () {
- this.element.removeClass( "ui-header-fixed ui-footer-fixed ui-header-fullscreen ui-footer-fullscreen in out fade slidedown slideup ui-fixed-hidden" );
- this.element.closest( ".ui-page" ).removeClass( "ui-page-header-fixed ui-page-footer-fixed ui-page-header-fullscreen ui-page-footer-fullscreen" );
+ viewElement.volume = value;
},
- refresh: function () {
- var $elPage = $( ".ui-page-active" );
- this.setHeaderFooter( $elPage );
- this._updateHeaderArea( $elPage );
- }
- });
-
- //auto self-init widgets
- $( document )
- .bind( "pagecreate create", function ( e ) {
- // DEPRECATED in 1.1: support for data-fullscreen=true|false on the page element.
- // This line ensures it still works, but we recommend moving the attribute to the toolbars themselves.
- if ( $( e.target ).jqmData( "fullscreen" ) ) {
- $( $.mobile.pagelayout.prototype.options.initSelector, e.target ).not( ":jqmData(fullscreen)" ).jqmData( "fullscreen", true );
+ width: function ( value ) {
+ if ( this.options.fullScreen ) {
+ return;
}
- $.mobile.pagelayout.prototype.enhanceWithin( e.target );
- });
-}( jQuery ));
+ var view = this.element,
+ wrap = view.parent( ".ui-multimediaview-wrap" );
+ if ( arguments.length === 0 ) {
+ return view.width();
+ }
+ if ( !this._isVideo ) {
+ wrap.width( value );
+ }
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Author: Wongi Lee <wongi11.lee@samsung.com>
- * Youmin Ha <youmin.ha@samsung.com>
- */
+ view.width( value );
+ this._resize();
+ },
-/**
- * Virtual List Widget for unlimited data.
- * To support more then 1,000 items, special list widget developed.
- * Fast initialize and light DOM tree.
- * DB connection and works like DB cursor.
- *
- * HTML Attributes:
- *
- * data-role: virtuallistview
- * data-template : jQuery.template ID that populate into virtual list
- * data-row : Optional. Set number of <li> elements that are used for data handling.
- *
- * ID : <UL> element that has "data-role=virtuallist" must have ID attribute.
- *
- * * APIs:
- *
- * create ( {
- * itemData: function ( idx ) { return json_obj; },
- * numItemData: number or function () { return number; },
- * cacheItemData: function ( minIdx, maxIdx ) {}
- * } )
- * : Create a virtuallist widget. At this moment, _create method is called.
- * args : A collection of options
- * itemData: A function that returns JSON object for given index. Mandatory.
- * numItemData: Total number of itemData. Mandatory.
- * cacheItemData: Virtuallist will ask itemData between minIdx and maxIdx.
- * Developers can implement this function for preparing data.
- * Optional.
- *
- * Events:
- *
- * touchstart : Temporary preventDefault applied on touchstart event to avoid broken screen.
- *
- * Examples:
- *
- * <script id="tmp-3-2-7" type="text/x-jquery-tmpl">
- * <li class="ui-li-3-2-7">
- * <span class="ui-li-text-main">${NAME}</span>
- * <img src="00_winset_icon_favorite_on.png" class="ui-li-icon-sub">
- * <span class="ui-li-text-sub">${ACTIVE}</span>
- * <span class="ui-li-text-sub2">${FROM}</span>
- * </li>
- * </script>
- *
- * <ul id="virtuallist-normal_3_2_7_ul" data-role="virtuallistview" data-template="tmp-3-2-7" data-dbtable="JSON_DATA" data-row="100">
- * </ul>
- *
- */
+ height: function ( value ) {
+ if ( !this._isVideo || this.options.fullScreen ) {
+ return;
+ }
-/**
- @class VirtualList
- In the Web environment, it is challenging to display a large amount of data in a list, such as displaying a contact list of over 1000 list items. It takes time to display the entire list in HTML and the DOM manipulation is complex.
+ var view = this.element;
- The virtual list widget is used to display a list of unlimited data elements on the screen for better performance. This widget provides easy access to databases to retrieve and display data. Virtual lists are based on the jQuery.template plugin as described in the jQuery documentation for jQuery.template plugin.
+ if ( arguments.length === 0 ) {
+ return view.height();
+ }
- To add a virtual list widget to the application, use the following code:
+ view.height( value );
+ this._resize();
+ },
- <script id="tmp-3-2-7" type="text/x-jquery-tmpl">
- <li class="ui-li-3-2-7">
- <span class="ui-li-text-main">${NAME}</span>
- <img src="00_winset_icon_favorite_on.png" class="ui-li-icon-sub"/>
- <span class="ui-li-text-sub">${ACTIVE}</span>
- <span class="ui-li-text-sub2">${FROM}</span>
- </li>
- </script>
- <ul id="vlist" data-role="virtuallistview" data-template="tmp-3-2-7" data-dbtable="JSON_DATA" data-row="100"></ul>
-*/
-/**
- @property {String} data-role
- Creates the virtual list view. The value must be set to virtuallistview.
- Only the >ul< element, which a id attribute defined, supports this option. Also, the vlLoadSuccess class attribute must be defined in the >ul< element to ensure that loading data from the database is complete.
-*/
-/**
- @property {String} data-template
- Defines the jQuery.template element ID.
- The jQuery.template must be defined. The template style can use rem units to support scalability.
-*/
-/**
- @property {Number} data-row
- Defines the number of virtual list child elements.
- The minimum value is 20 and the default value is 100. As the value gets higher, the loading time increases while the system performance improves. So you need to pick a value that provides the best performance without excessive loading time.
-*/
-/**
- @method create
- @param {function} itemData(index)
- : function itemData(index) returns the JSON object matched with the given index. The index value is between 0 and numItemData-1.
- @param {Number} numItemData
- : number numItemData or function numItemData() defines or returns a static number of items.
- @param {function} cacheItemData(minIndex, maxIndex)
- : function cacheItemData(minIndex, maxIndex) prepares the JSON data. This method is called before calling the itemData() method with index values between minIndex and maxIndex.
-*/
+ fullScreen: function ( value ) {
+ if ( !this._isVideo ) {
+ return;
+ }
-(function ( $, undefined ) {
+ var view = this.element,
+ option = this.options;
- /* Code for Virtual List Demo */
- var listCountPerPage = {}, /* Keeps track of the number of lists per page UID. This allows support for multiple nested list in the same page. https://github.com/jquery/jquery-mobile/issues/1617 */
- _NO_SCROLL = 0, /* ENUM */
- _SCROLL_DOWN = 1, /* ENUM */
- _SCROLL_UP = -1; /* ENUM */
+ if ( arguments.length === 0 ) {
+ return option.fullScreen;
+ }
- $.widget( "tizen.virtuallistview", $.mobile.widget, {
- options: {
- theme: "s",
- countTheme: "s",
- headerTheme: "s",
- dividerTheme: "s",
- splitIcon: "arrow-r",
- splitTheme: "s",
- inset: false,
- id: "", /* Virtual list UL elemet's ID */
- childSelector: " li", /* To support swipe list */
- dbtable: "",
- template : "",
- dbkey: false, /* Data's unique Key */
- scrollview: false,
- row: 100,
- page_buf: 30,
- initSelector: ":jqmData(role='virtuallistview')"
- },
+ view.parents( ".ui-scrollview-clip" ).scrollview( "scrollTo", 0, 0 );
- _stylerMouseUp: function () {
- $( this ).addClass( "ui-btn-up-s" );
- $( this ).removeClass( "ui-btn-down-s" );
- },
+ this.options.fullScreen = value;
- _stylerMouseDown: function () {
- $( this ).addClass( "ui-btn-down-s" );
- $( this ).removeClass( "ui-btn-up-s" );
+ this._resize();
},
- _stylerMouseOver: function () {
- $( this ).toggleClass( "ui-btn-hover-s" );
- },
+ refresh: function () {
+ this._resize();
+ }
+ });
- _stylerMouseOut: function () {
- $( this ).toggleClass( "ui-btn-hover-s" );
- $( this ).addClass( "ui-btn-up-s" );
- $( this ).removeClass( "ui-btn-down-s" );
- },
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $.tizen.multimediaview.prototype.enhanceWithin( e.target );
+ }).bind( "pagechange", function ( e ) {
+ $( e.target ).find( ".ui-multimediaview" ).each( function () {
+ var view = $( this ),
+ viewElement = view[0];
+
+ if ( viewElement.autoplay ) {
+ viewElement.play();
+ }
+ view.multimediaview( "refresh" );
+ });
+ }).bind( "pagebeforechange", function ( e ) {
+ $( e.target ).find( ".ui-multimediaview" ).each( function () {
+ var view = $( this ),
+ viewElement = view[0],
+ isFullscreen = view.multimediaview( "fullScreen" );
- // ?
- // this virtuallistview object
- // @param[in] template template name(string)
- _pushData: function ( template ) {
- var o = this.options,
- i,
- myTemplate = $( "#" + template ), // Get template object
- // NOTE: o.row = # of rows handled at once. Default value is 100.
- lastIndex = ( o.row > this._numItemData ? this._numItemData : o.row ), // last index of handled data
- htmlData;
+ if ( isFullscreen ) {
+ view.multimediaview( "fullScreen", !isFullscreen );
+ }
- for ( i = 0; i < lastIndex; i++ ) {
- htmlData = myTemplate.tmpl( this._itemData( i ) ); // Make rows with template,
- $( o.id ).append( $( htmlData ).attr( 'id', o.itemIDPrefix + i ) ); // and append it to the vlist object
+ if ( viewElement.played.length !== 0 ) {
+ viewElement.pause();
}
+ });
+ });
- // After pushing data re-style virtuallist widget
- $( o.id ).trigger( "create" );
- },
+ $( window ).bind( "resize orientationchange", function ( e ) {
+ $( ".ui-page-active" ).find( ".ui-multimediaview" ).multimediaview( "refresh" );
+ });
- // Set children <li> elements' position
- //
- // this: virtuallist element
- // event: virtuallistview.options
- // TODO: Why this arg name is 'event'? Not resonable.
- // (this function is not called with event element as args!)
- _reposition: function ( event ) {
- var o,
- t = this,
- padding,
- margin;
+} ( jQuery, document, window ) );
- if ( event.data ) {
- o = event.data;
- } else {
- o = event;
- }
- if ( $( o.id + o.childSelector ).size() > 0 ) { // $("#vlistid li")
- // first child's top position
- // NOTE: the first element may not be '0'!!!
- t._title_h = $( o.id + o.childSelector + ':first' ).position().top;
- // first child's outer height (TODO: reuse selected items)
- t._line_h = $( o.id + o.childSelector + ':first' ).outerHeight();
- // container(vlist element)'s innerwidth
- t._container_w = $( o.id ).innerWidth();
- // get sum of container's left/right padding
- padding = parseInt( $( o.id + o.childSelector ).css( "padding-left" ), 10 )
- + parseInt( $( o.id + o.childSelector ).css( "padding-right" ), 10 );
+/*
+ * jQuery Mobile Widget @VERSION
+ *
+ * TODO: remove unnecessary codes....
+ *
+ * This software is licensed under the MIT licence (as defined by the OSI at
+ * http://www.opensource.org/licenses/mit-license.php)
+ *
+ * ***************************************************************************
+ * Copyright (C) 2011 by Intel Corporation Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Authors: Kalyan Kondapally <kalyan.kondapally@intel.com>
+ */
- // Add CSS to all <li> elements
- // * absolute position
- // * btn-up
- // * mouse up/down/over/out styles
- $( o.id + ">" + o.childSelector )
- .addClass( "position_absolute" )
- .addClass( "ui-btn-up-s" )
- .bind( "mouseup", t._stylerMouseUp )
- .bind( "mousedown", t._stylerMouseDown )
- .bind( "mouseover", t._stylerMouseOver )
- .bind( "mouseout", t._stylerMouseOut );
- }
+ensureNS("jQuery.mobile.tizen");
- // Set absolute top/left position of each <li>
- $( o.id + ">" + o.childSelector ).each( function ( index ) {
- margin = parseInt( $( this ).css( "margin-left" ), 10 )
- + parseInt( $( this ).css( "margin-right" ), 10 );
+(function () {
+jQuery.extend(jQuery.mobile.tizen, {
+ disableSelection: function (element) {
+ this.enableSelection(
+ $(element).find('*').not( 'input, [type="text"], textarea' ),
+ 'none'
+ );
+ return true;
+ },
- $( this ).css( "top", t._title_h + t._line_h * index + 'px' )
- .css( "width", t._container_w - padding - margin );
- } );
+ enableSelection: function (element, value) {
+ var val;
+ switch ( value ) {
+ case 'text' :
+ case 'auto' :
+ case 'none' :
+ val = value;
+ break;
+ default :
+ val = 'auto';
+ break;
+ }
+ return $(element).css( {
+ 'user-select': val,
+ '-moz-user-select': val,
+ '-webkit-user-select': val,
+ '-o-user-select': val,
+ '-ms-transform': val
+ } );
+ },
- // Set Max Listview Height
- $( o.id ).height( t._numItemData * t._line_h );
- },
+ disableContextMenu: function(element) {
+ var self = this;
+ $(element).find('*').each( function() {
+ if( ( $(this).get(0).tagName !== 'INPUT' &&
+ $(this).attr("type") !== 'text' ) &&
+ $(this).get(0).tagName !== 'TEXTAREA' ) {
+ self._disableContextMenu( this );
+ }
+ } );
+ },
- // Resize each listitem's width
- _resize: function ( event ) {
- var o, // 'ul'
- t = this,
- li,
- padding,
- margin;
+ _disableContextMenu: function(element) {
- if ( event.data ) {
- o = event.data;
- } else {
- o = event;
- }
- li = $( o ).children( o.childSelector )
+ $(element).each( function() {
+ $(this).bind("contextmenu", function( event ) {
+ return false;
+ } );
+ } );
+ },
- t._container_w = $( o ).width();
+ enableContextMenu: function(element) {
+ $(element).each( function() {
+ $(this).unbind( "contextmenu" );
+ } );
+ },
- padding = parseInt( li.css( "padding-left" ), 10 )
- + parseInt( li.css( "padding-right" ), 10 );
+ // Get document-relative mouse coordinates from a given event
+ // From: http://www.quirksmode.org/js/events_properties.html#position
+ documentRelativeCoordsFromEvent: function(ev) {
+ var e = ev ? ev : window.event,
+ client = { x: e.clientX, y: e.clientY },
+ page = { x: e.pageX, y: e.pageY },
+ posx = 0,
+ posy = 0;
- li.each( function ( index, obj ) {
- margin = parseInt( $( this ).css( "margin-left" ), 10 )
- + parseInt( $( this ).css( "margin-right" ), 10 );
- $( this ).css( "width", t._container_w - padding - margin );
- } );
- },
+ // Grab useful coordinates from touch events
+ if (e.type.match(/^touch/)) {
+ page = {
+ x: e.originalEvent.targetTouches[0].pageX,
+ y: e.originalEvent.targetTouches[0].pageY
+ };
+ client = {
+ x: e.originalEvent.targetTouches[0].clientX,
+ y: e.originalEvent.targetTouches[0].clientY
+ };
+ }
- // New scrollmove function supporting scrollTo
- _scrollmove: function ( ev ) {
- var t = ev.data, // vlist (JQM object)
- o = t.options, // options
- prevTopBufLen = t._num_top_items, // Previous(remembered) top buf length
- timerInterval = 100,
- i,
- _scrollView,
- _normalScroll;
+ if (page.x || page.y) {
+ posx = page.x;
+ posy = page.y;
+ }
+ else
+ if (client.x || client.y) {
+ posx = client.x + document.body.scrollLeft + document.documentElement.scrollLeft;
+ posy = client.y + document.body.scrollTop + document.documentElement.scrollTop;
+ }
- _scrollView = {
- viewTop: function ( ) {
- var sv = $( o.id ).parentsUntil( ".ui-page" ).find( ".ui-scrollview-view" ),
- svTrans = sv.css( "-webkit-transform" ),
- svTransVal = "0,0,0,0,0,0";
- if ( svTrans ) {
- svTransVal = svTrans.replace( /matrix\s*\((.*)\)/, "$1" ); // matrix(a,c,b,d,tx,ty)
- }
- return - parseInt( svTransVal.split(',')[5], 10 );
- }
- };
- _normalScroll = {
- viewTop: function ( ) {
- return $( window ).scrollTop( ); // TODO: - _line_h?
- }
- };
- // Get current view top position
- function viewTop ( ) {
- return o.scrollview ? _scrollView.viewTop() : _normalScroll.viewTop();
- }
- // log function for debug
- function log ( msg ) {
- var debug = false;
- if ( debug ) {
- console.log( ">>virtualllist: " + msg );
- }
- }
+ return { x: posx, y: posy };
+ },
+
+ // TODO : offsetX, offsetY. touch events don't have offsetX and offsetY. support for touch devices.
+ // check algorithm...
+ targetRelativeCoordsFromEvent: function(e) {
+ var coords = { x: e.offsetX, y: e.offsetY };
+
+ if (coords.x === undefined || isNaN(coords.x) ||
+ coords.y === undefined || isNaN(coords.y)) {
+ var offset = $(e.target).offset();
+ //coords = documentRelativeCoordsFromEvent(e); // Old code. Must be checked again.
+ coords = $.mobile.tizen.documentRelativeCoordsFromEvent(e);
+ coords.x -= offset.left;
+ coords.y -= offset.top;
+ }
- // Timer interval function
- // @param[in] vl virtuallist object (JQM object)
- function timerMove ( vl, undefined ) {
- var cy, // current y position
- cti, // current top idx
- cbi, // current bottom idx
- oti = vl._first_index, // old top idx
- obi = vl._last_index, // old botton idx
- dti, // delta of top idx
- fromIdx,
- toIdx, // index range to be moved
- delta, // moveItem delta
- rowLen = vl.options.row, // max. # of items handled at once
- bufSize, // top/bottom buffer size. unit: # of items
- i;
+ return coords;
+ }
+});
- // subroutine: Move itemContents in i2 into i1
- function moveItemContents( vl, i1, i2 ) {
- // TODO: Find a efficient way to replace data!
- // Assumption: i1 and i2 has same children.
- var NODETYPE = { ELEMENT_NODE: 1, TEXT_NODE: 3 },
- c1, // child item 1 (old)
- c2, // child item 2 (new)
- newText,
- newImg,
- i;
+})();
- $( i1 ).find( ".ui-li-text-main", ".ui-li-text-sub", ".ui-li-text-sub2", "ui-btn-text" ).each( function ( index ) {
- c1 = $( this );
- newText = $( i2 ).find( ".ui-li-text-main", ".ui-li-text-sub", "ui-btn-text" ).eq( index ).text();
- $( c1 ).contents().filter( function () {
- return ( this.nodeType == NODETYPE.TEXT_NODE );
- } ).get( 0 ).data = newText;
- } );
- $( i1 ).find( "img" ).each( function ( imgIdx ) {
- var c1 = $( this );
- newImg = $( i2 ).find( "img" ).eq( imgIdx ).attr( "src" );
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Author: Kangsik Kim <kangsik81.kim@samsung.com>
+ * Youmin Ha <youmin.ha@samsung.com>
+*/
- $( c1 ).attr( "src", newImg );
- } );
+/**
+ * In the web environment, it is challenging to display a large amount of data in a grid.
+ * When an application needs to show, for example, image gallery with over 1,000 images,
+ * the same enormous data must be inserted into a HTML document.
+ * It takes a long time to display the data and manipulating DOM is complex.
+ * The virtual grid widget supports storing unlimited data without performance issues
+ * by reusing a limited number of grid elements.
+ * The virtual grid widget is based on the jQuery.template plug-in
+ * For more information, see jQuery.template.
+ *
+ * HTML Attributes:
+ *
+ * data-role: virtualgrid
+ * data-template : Has the ID of the jQuery.template element.
+ * jQuery.template for a virtual grid must be defined.
+ * Style for template would use rem unit to support scalability.
+ * data-direction : This option define the direction of the scroll.
+ * You must choose one of the 'x' and 'y' (Default : y)
+ * data-rotation : This option defines whether or not the circulation of the data.
+ * If option is 'true' and scroll is reached the last data,
+ * Widget will present the first data on the screen.
+ * If option is ‘false’, Widget will operate like a scrollview.
+ *
+ * ID : <DIV> element that has "data-role=virtualgrid" must have ID attribute.
+ *
+ * APIs:
+ *
+ * create ( {
+ * itemData: function ( idx ) { return json_obj; },
+ * numItemData: number or function () { return number; },
+ * cacheItemData: function ( minIdx, maxIdx ) {}
+ * } )
+ * : Create VirtualGrid widget. At this moment, _create method is called.
+ * args : A collection of options
+ * itemData: A function that returns JSON object for given index. Mandatory.
+ * numItemData: Total number of itemData. Mandatory.
+ * cacheItemData: Virtuallist will ask itemData between minIdx and maxIdx.
+ * Developers can implement this function for preparing data.
+ * Optional.
+ *
+ * centerTo ( selector )
+ * : Center the particular item with the class name on the VirtualGrid's display area.;
+ * i.e., this method selects an item in the data elements of grid using the class name and
+ * moves the data elements inside the widget to display the row containing the selected item
+ * in the middle of the screen.
+ * If multiple items are matched with the class name, the first matched item will be selected.
+ * This method is only available when "data-rotation" attribute is "true".
+ *
+ * resize ()
+ * : Rearrange items to fit a new widget size.
+ *
+ * Events:
+ * scrollstart : : This event triggers when a user begin to move the scroll on VirtualGrid.
+ * scrollupdate : : This event triggers while a user moves the scroll on VirtualGrid.
+ * scrollstop : This event triggers when a user stop the scroll on VirtualGrid.
+ * select : This event triggers when a cell is selected.
+ *
+ * Examples:
+ *
+ * <script id="tizen-demo-namecard" type="text/x-jquery-tmpl">
+ * <div class="ui-demo-namecard">
+ * <div class="ui-demo-namecard-pic">
+ * <img class="ui-demo-namecard-pic-img" src="${TEAM_LOGO}" />
+ * </div>
+ * <div class="ui-demo-namecard-contents">
+ * <span class="name ui-li-text-main">${NAME}</span>
+ * <span class="active ui-li-text-sub">${ACTIVE}</span>
+ * <span class="from ui-li-text-sub">${FROM}</span>
+ * </div>
+ * </div>
+ * </script>
+ * <div id="virtualgrid-demo" data-role="virtualgrid" data-template="tizen-demo-namecard" >
+ * </div>
+ *
+ */
- $( i1 ).removeData( ); // Clear old data
- }
+// most of following codes are derived from jquery.mobile.scrollview.js
- // subroutine: Move item
- function moveItem( vl, fromIdx, toIdx ) {
- var itemData, // data from itemData()
- item, // item element
- newItem, // new item element
- tmpl; // template
+/**
+ @class VirtualGrid
+ In the Web environment, it is challenging to display large amount of data in a list, such as displaying a contact list of over 1000 list items. It takes time to display the entire list in HTML and the DOM manipulation is complex.
- log( ">> move item: " + fromIdx + " --> " + toIdx );
+ The virtual grid widget is used to display a list of unlimited data elements on the screen for better performance. This widget displays the data in the grid format by reusing the existing grid control space. Virtual grids are based on the jQuery.template plugin as described in the jQuery documentation for jQuery.template plugin.
- // Find current item
- item = $( '#' + vl.options.itemIDPrefix + fromIdx ); // TODO: refactor ID generation!
- if ( ! item || ! item.length ) {
- return false;
- }
+ To add a virtual grid widget to the application, use the following code:
- // Get new item
- tmpl = $( "#" + vl.options.template );
- if ( tmpl ) {
- newItem = tmpl.tmpl( vl._itemData( toIdx ) );
+ <script id="tizen-demo-namecard" type="text/x-jquery-tmpl">
+ <div class="ui-demo-namecard">
+ <div class="ui-demo-namecard-pic">
+ <img class="ui-demo-namecard-pic-img" src="${TEAM_LOGO}" />
+ </div>
+ <div class="ui-demo-namecard-contents">
+ <span class="name ui-li-text-main">${NAME}</span>
+ </div>
+ </div>
+ </script>
+ <div id="virtualgrid-demo" data-role="virtualgrid" data-template="tizen-demo-namecard">
+ </div>
+*/
+/**
+ @property {String} data-template
+ Specifies the jQuery.template element ID.
+ The jQuery.template must be defined. The template style can use rem units to support scalability.
+*/
+/**
+ @property {String} data-direction
+ Defines the scroll direction. The direction options are x (horizontal) and y (vertical).
+ The default value is y.
+*/
+/**
+ @property {Boolean} data-rotation
+ Defines whether the data elements are displayed from the beginning of the list again once the end of file is reached.
+ The default value is false.
+*/
+/**
+ @event scrollstart
+ The scrollstart event is fired when the user starts scrolling through the grid:
- // TODO: Consider touch block while moving?
+ <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
+ $(".selector").on("scrollstart", function(event, ui)
+ {
+ // Handle the scrollstart event
+ });
+*/
+/**
+ @event scrollupdate
+ The scrollupdate event is fired when the user moves the scroll bar in the grid:
- // Move item contents
- moveItemContents( vl, item, newItem );
+ <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
+ $(".selector").on("scrollupdate", function(event, ui)
+ {
+ // Handle the scrollupdate event
+ });
+*/
+/**
+ @event scrollstop
+ The scrollstop event is fired when the user stops scrolling:
- // clean up temporary item
- newItem.remove();
- }
+ <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
+ $(".selector").on("scrollstop", function(event, ui)
+ {
+ // Handle the scrollstop event
+ });
+*/
+/**
+ @event select
+ The select event is fired when a virtual grid cell is selected:
+
+ <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
+ $(".selector").on("select", function(event, ui)
+ {
+ // Handle the select event
+ });
+*/
+/**
+ @method create
+ @param {function} itemData(index)
+ @param {Number} numItemData
+ @param {function} cacheItemData(minIndex, maxIndex)
+ The create method is used to call the jQuery _create method. In the method parameters:
+
+ function itemData(index) returns the JSON object matched with the given index. The index value is between 0 and numItemData-1.<br/>
+ number numItemData or function numItemData() defines or returns a static number of items.<br/>
+ function cacheItemData(minIndex, maxIndex) prepares the JSON data. This method is called before calling the itemData() method with index values between minIndex and maxIndex.<br/>
+
+ <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
+ function itemData(idx)
+ {
+ return DATA[idx];
+ }
+ function cacheItemData(minIdx, maxIdx)
+ {
+ // Prepare JSON data between minIdx and maxIdx
+ }
+ var numItemData = DATA.length;
+ $(".selector").virtualgrid("create",
+ {
+ itemData, numItemData, cacheItemData
+ });
+*/
+/**
+ @method centerTo
+ The centerTo method is used to center the particular item with the class name on the VirtualGrid's display area. If multiple items are matched with the class name, the first matched item will be selected. This method is only available when "data-rotation" attribute is "true".
- // Move position, and set id
- item.css( 'top', toIdx * vl._line_h )
- .attr( 'id' , vl.options.itemIDPrefix + toIdx ); // TODO: refactor ID generation!
+ <div data-role="virtualgrid" data-scroll="y" data-rotation="true" data-template="tizen-demo-namecard"></div>
+ $(".selector").virtualgrid("centerTo", selector);
+*/
+/**
+ @method resize
+ The resize method is used to rearrange items to fit a new widget size. :
- // TODO: Apply jqmdata? check following old code;
- // $( oldItem ).removeData( ); // Clear old data
- // if (key) { $( oldItem ).data( key, $( newItem ).data( key ) ); }
+ <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
+ $(".selector").virtualgrid("resize");
- return true;
- }
+ @since Tizen2.0
+*/
+( function ( $, window, document, undefined ) {
- // Get current view position
- cy = viewTop();
+ function circularNum ( num, total ) {
+ var n = num % total;
+ if ( n < 0 ) {
+ n = total + n;
+ }
+ return n;
+ }
- // Calculate bufSize: rowLen / 3
- // NOTE: Assumption: total row length = visible items * 3 (upper+visible+lower)
- bufSize = Math.ceil( rowLen / 3 );
+ function MomentumTracker ( options ) {
+ this.options = $.extend( {}, options );
+ this.easing = "easeOutQuad";
+ this.reset();
+ }
- // Calculate current top/bottom index (to be applied)
- // top index = current position / line height
- cti = Math.floor( cy / vl._line_h ) - bufSize; // TODO: consider buffer!
- cbi = cti + rowLen - 1;
+ var tstates = {
+ scrolling : 0,
+ done : 1
+ },
+ _OVERFLOW_DIR_NONE = 0, /* ENUM */
+ _OVERFLOW_DIR_UP = 1, /* ENUM */
+ _OVERFLOW_DIR_DOWN = -1, /* ENUM */
+ imgTagSrcAttrRE = /src\s*=\s*[\"\'][\w\/.]+.[A-z]+[\"\']/;
- if ( cti < 0 ) { // Top boundary check
- cbi += ( - cti );
- cti = 0;
- } else if ( cbi > ( vl._numItemData - 1 ) ) { // Bottom boundary check
- cti -= ( cbi - ( vl._numItemData - 1 ) );
- cbi = ( vl._numItemData - 1 );
- }
+ function getCurrentTime () {
+ return Date.now();
+ }
- // Calculate dti
- dti = cti - oti;
- log( "cy=" + cy + ", oti=" + oti + ", obi=" + obi + ", cti=" + cti + ", cbi=" + cbi + ", dti=" + dti );
+ $.extend( MomentumTracker.prototype, {
+ start : function ( pos, speed, duration ) {
+ this.state = ( speed !== 0 ) ? tstates.scrolling : tstates.done;
+ this.pos = pos;
+ this.speed = speed;
+ this.duration = duration;
- // switch: dti = 0 --> timer stop condition: delta=0 or scrollstop event comes. END.
- if ( 0 == dti ) {
- // Check timer runtime
- vl.timerStillCount += 1;
- if ( vl.timerStillCount < 12 ) { // check count ( TODO: test and adjust )
- log("dti=0 " + vl.timerStillCount + " times");
- vl.timerMoveID = setTimeout( timerMove, timerInterval, vl ); // run once more
- return;
- }
+ this.fromPos = 0;
+ this.toPos = 0;
- log("dti=0 " + vl.timerStillCount + " times. End timer.");
- vl.timerStillCount = 0;
- // Stop timer
- if ( vl.timerMoveID ) {
- clearTimeout( vl.timerMoveID );
- vl.timerMoveID = null;
- }
- } else {
- // switch: dti >= # of max elements --> total replace.
- vl.timerStillCount = 0; // Reset still counter
+ this.startTime = getCurrentTime();
+ },
- if ( Math.abs( dti ) >= rowLen ) {
- fromIdx = oti;
- toIdx = obi;
- delta = dti;
- log( ">>> WHOLE CHANGE! delta=" + delta );
- } else {
- // switch: dti < # of max elements --> move t2b or b2t until new top/bottom idx is covered
- if ( dti > 0 ) {
- fromIdx = oti;
- toIdx = oti + dti - 1;
- delta = rowLen;
- } else {
- fromIdx = obi + dti + 1; // dti < 0
- toIdx = obi;
- delta = -rowLen;
- }
- log( ">>> partial change. delta=" + delta );
- }
+ reset : function () {
+ this.state = tstates.done;
+ this.pos = 0;
+ this.speed = 0;
+ this.duration = 0;
+ },
- // Move items
- for ( i = fromIdx; i <= toIdx; i++ ) {
- moveItem( vl, i, i + delta ); // Change data and position
- }
+ update : function () {
+ var state = this.state, duration, elapsed, dx, x;
- // Store current top/bottom idx into vl
- vl._first_index = cti;
- vl._last_index = cbi;
+ if ( state == tstates.done ) {
+ return this.pos;
+ }
+ duration = this.duration;
+ elapsed = getCurrentTime () - this.startTime;
+ elapsed = elapsed > duration ? duration : elapsed;
+ dx = this.speed * ( 1 - $.easing[this.easing]( elapsed / duration, elapsed, 0, 1, duration ) );
+ x = this.pos + ( dx / 2 );
+ this.pos = x;
- // Register timer to check again
- vl.timerMoveID = setTimeout( timerMove, timerInterval, vl );
- }
- return; // End of function
+ if ( elapsed >= duration ) {
+ this.state = tstates.done;
}
+ return this.pos;
+ },
- // ==== function start ====
+ done : function () {
+ return this.state == tstates.done;
+ },
- t.timerStillCount = 0; // Count do-nothing time. For behavior tuning.
+ getPosition : function () {
+ return this.pos;
+ }
+ });
- // If a timer function is alive, clear it
- if ( t.timerMoveID ) {
- clearTimeout( t.timerMoveID );
- t.timerMoveID = null;
- }
- // run TimerMove()
- timerMove( t );
+ jQuery.widget ( "mobile.virtualgrid", jQuery.mobile.widget, {
+ options : {
+ // virtualgrid option
+ template : "",
+ direction : "y",
+ rotation : false
},
- _recreate: function ( newArray ) {
- var t = this,
- o = this.options;
+ create : function () {
+ this._create.apply( this, arguments );
+ },
- $( o.id ).empty();
+ _create : function ( args ) {
+ $.extend( this, {
+ // view
+ _$view : null,
+ _$clip : null,
+ _$rows : null,
+ _tracker : null,
+ _viewSize : 0,
+ _clipSize : 0,
+ _cellSize : undefined,
+ _currentItemCount : 0,
+ _itemCount : 1,
+ _inheritedSize : null,
- t._numItemData = newArray.length;
- t._direction = _NO_SCROLL;
- t._first_index = 0;
- t._last_index = o.row - 1;
+ // timer
+ _timerInterval : 0,
+ _timerID : 0,
+ _timerCB : null,
+ _lastMove : null,
- t._pushData( o.template );
+ // Data
+ _itemData : function ( idx ) { return null; },
+ _numItemData : 0,
+ _cacheItemData : function ( minIdx, maxIdx ) { },
+ _totalRowCnt : 0,
+ _templateText : null,
+ _maxViewSize : 0,
+ _modifyViewPos : 0,
+ _maxSizeExceptClip : 0,
+ _maxSize : 0,
- if (o.childSelector == " ul" ) {
- $( o.id + " ul" ).swipelist();
- }
+ // axis - ( true : x , false : y )
+ _direction : false,
+ _didDrag : true,
+ _reservedPos : 0,
+ _scalableSize : 0,
+ _eventPos : 0,
+ _nextPos : 0,
+ _movePos : 0,
+ _lastY : 0,
+ _speedY : 0,
+ _lastX : 0,
+ _speedX : 0,
+ _rowsPerView : 0,
+ _fragment : null,
- $( o.id ).virtuallistview();
+ _filterRatio : 0.9,
- t.refresh( true );
+ _overflowStartPos : 0,
+ _overflowDir : 0,
+ _overflowMaxDragDist : 100
+ });
- t._reposition( o );
- },
+ var self = this,
+ $dom = $( self.element ),
+ opts = self.options,
+ $item = null;
- // Init virtuallistview
- // this virtuallistview object
- _initList: function () {
- var t = this,
- o = this.options;
+ // itemData
+ // If mandatory options are not given, Do nothing.
+ if ( !args ) {
+ return ;
+ }
- /* After AJAX loading success */
+ if ( !self._loadData( args ) ) {
+ return;
+ }
- // Put initial <li> elements
- t._pushData( o.template );
+ // make a fragment.
+ self._fragment = document.createDocumentFragment();
- // find a parent page, and run _reposition() at 'pageshow' event
- // TODO: Consider replace parentsUntil().parent() to parent('.ui-page') ???
- $( o.id ).parentsUntil( ".ui-page" ).parent().one( "pageshow", function () {
- setTimeout( function () {
- t._reposition( o );
- }, 0);
- });
+ // read defined properties(width and height) from dom element.
+ self._inheritedSize = self._getinheritedSize( self.element );
- // Bind _scrollmove() at 'scrollstart.virtuallist' event
- $( document ).bind( "scrollstart.virtuallist scrollstop.vrituallist", t, t._scrollmove );
+ // set a scroll direction.
+ self._direction = opts.direction === 'x' ? true : false;
- // Bind _resize()
- $( window ).on( "throttledresize", $( o.id ), t._resize );
+ // make view layer
+ self._$clip = $dom.addClass( "ui-scrollview-clip" ).addClass( "ui-virtualgrid-view" );
+ $item = $( document.createElement( "div" ) ).addClass( "ui-scrollview-view" );
+ self._clipSize = self._calculateClipSize();
+ self._$clip.append( $item );
+ self._$view = $item;
+ self._$clip.css( "overflow", "hidden" );
+ self._$view.css( "overflow", "hidden" );
- // when ul is a childselector, assume that this is also a swipelist,
- // and run swipelist constructor
- if ( o.childSelector == " ul" ) {
- $( o.id + " ul" ).swipelist();
- }
+ // inherit from scrollview widget.
+ self._scrollView = $.tizen.scrollview.prototype;
+ self._initScrollView();
- t.refresh( true );
- },
+ // create tracker.
+ self._createTracker();
+ self._makePositioned( self._$clip );
+ self._timerInterval = 1000 / self.options.fps;
- create: function () {
- var o = this.options;
+ self._timerID = 0;
+ self._timerCB = function () {
+ self._handleMomentumScroll();
+ };
+ $dom.closest( ".ui-content" ).addClass( "ui-virtualgrid-content" ).css( "overflow", "hidden" );
- /* external API for AJAX callback */
- this._create.apply( this, arguments );
+ // add event handler.
+ self._addBehaviors();
- // TODO: remove this line? _initList() calls reposition...
- this._reposition( o );
+ self._currentItemCount = 0;
+ self._createOverflowArea();
+ self._createScrollBar();
+ self.refresh();
},
- _create: function ( args ) {
- // Extend instance variables
- $.extend( this, {
- _itemData : function ( idx ) { return null; },
- _numItemData : 0,
- _cacheItemData : function ( minIdx, maxIdx ) { },
- _title_h : 0,
- _container_w : 0,
- _minimum_row : 100,
- _direction : _NO_SCROLL,
- _first_index : 0,
- _last_index : 0,
- _num_top_items : 0 // By scroll move, number of hidden elements.
- } );
+ // The argument is checked for compliance with the specified format.
+ // @param args : Object
+ // @return boolean
+ _loadData : function ( args ) {
+ var self = this;
- // local variables
- var t = this,
- o = this.options,
- $el = this.element,
- shortcutsContainer = $('<div class="ui-virtuallist"/>'),
- shortcutsList = $('<ul></ul>'),
- dividers = $el.find(':jqmData(role="virtuallistview" )'),
- lastListItem = null,
- shortcutscroll = this,
- dbtable_name,
- dbtable;
+ if ( args.itemData && typeof args.itemData == 'function' ) {
+ self._itemData = args.itemData;
+ } else {
+ return false;
+ }
+ if ( args.numItemData ) {
+ if ( typeof args.numItemData == 'function' ) {
+ self._numItemData = args.numItemData( );
+ } else if ( typeof args.numItemData == 'number' ) {
+ self._numItemData = args.numItemData;
+ } else {
+ return false;
+ }
+ } else {
+ return false;
+ }
+ self._getObjectNames( self._itemData( 0 ) );
+ return true;
+ },
+ // Make up the first screen.
+ _initLayout: function () {
+ var self = this,
+ opts = self.options,
+ i,
+ $row;
- // Add CSS classes to $el (=virtuallistview)
- $el.addClass( function ( i, orig ) {
- return orig + " ui-listview ui-virtual-list-container" + ( t.options.inset ? " ui-listview-inset ui-corner-all ui-shadow " : "" );
- });
+ for ( i = -1; i < self._rowsPerView + 1; i += 1 ) {
+ $row = self._$rows[ circularNum( i, self._$rows.length ) ];
+ self._$view.append( $row );
+ }
+ self._setElementTransform( -self._cellSize );
- // keep the vlist's ID
- o.itemIDPrefix = $el.attr( "id" ) + '_';
- o.id = "#" + $el.attr( "id" );
+ self._replaceRow( self._$view[0].firstChild, self._totalRowCnt - 1 );
+ if ( opts.rotation && self._rowsPerView >= self._totalRowCnt ) {
+ self._replaceRow( self._$view[0].lastChild, 0 );
+ }
+ self._setViewSize();
+ },
- // when page hides, empty all child elements
- $( o.id ).bind( "pagehide", function ( e ) {
- $( o.id ).empty();
- });
+ _setViewSize : function () {
+ var self = this,
+ height = 0,
+ width = 0;
- // Find if scrollview is used
- if ( $( ".ui-scrollview-clip" ).size() > 0 ) {
- o.scrollview = true;
+ if ( self._direction ) {
+ width = self._cellSize * ( self._rowsPerView + 2 );
+ width = parseInt( width, 10 ) + 1;
+ self._$view.width( width );
+ self._viewSize = self._$view.width();
} else {
- o.scrollview = false;
+ self._$view.height( self._cellSize * ( self._rowsPerView + 2 ) );
+ self._$clip.height( self._clipSize );
+ self._viewSize = self._$view.height();
}
+ },
- // Calculate page buffer size
- if ( $el.data( "row" ) ) {
- o.row = $el.data( "row" );
+ _getViewWidth : function () {
+ var self = this;
+ return self._maxSize;
+ },
- if ( o.row < t._minimum_row ) {
- o.row = t._minimum_row;
- }
+ _getViewHeight : function () {
+ var self = this;
+ return self._maxSize;
+ },
- o.page_buf = parseInt( ( o.row / 2 ), 10 );
+ refresh : function () {
+ var self = this,
+ opts = self.options,
+ width = 0,
+ height = 0,
+ $template = null;
+
+ $template = $( "#" + opts.template );
+ if ( !$template ) {
+ return ;
}
+ self._templateText = self._insertAriaAttrToTmpl( $template.text() );
- // Get arguments
- if ( args ) {
- if ( args.itemData && typeof args.itemData == 'function' ) {
- t._itemData = args.itemData;
- } else {
- return;
- }
- if ( args.numItemData ) {
- if ( typeof args.numItemData == 'function' ) {
- t._numItemData = args.numItemData( );
- } else if ( typeof args.numItemData == 'number' ) {
- t._numItemData = args.numItemData;
- } else {
- return;
- }
- } else {
- return;
- }
- } else { // No option is given
- // Legacy support: dbtable
- console.warn( "WARNING: The data interface of virtuallist is changed. \nOld data interface(data-dbtable) is still supported, but will be removed in next version. \nPlease fix your code soon!" );
+ width = self._calculateClipWidth();
+ height = self._calculateClipHeight();
+ self._$view.width( width ).height( height );
+ self._$clip.width( width ).height( height );
- /* After DB Load complete, Init Vritual list */
- if ( $( o.id ).hasClass( "vlLoadSuccess" ) ) {
- dbtable_name = $el.jqmData('dbtable');
- dbtable = window[ dbtable_name ];
+ self._clipSize = self._calculateClipSize();
+ self._calculateColumnSize();
+ self._initPageProperty();
+ self._setScrollBarSize();
+ },
- $( o.id ).empty();
+ _initPageProperty : function () {
+ var self = this,
+ rowsPerView = 0,
+ $child,
+ columnCount = 0,
+ totalRowCnt = 0,
+ attributeName = self._direction ? "width" : "height";
- if ( !dbtable ) {
- dbtable = { };
- }
+ columnCount = self._calculateColumnCount();
- t._itemData = function ( idx ) {
- return dbtable[ idx ];
- };
- t._numItemData = dbtable.length;
- } else {
- return; // Do nothing
- }
+ totalRowCnt = parseInt( self._numItemData / columnCount, 10 );
+ self._totalRowCnt = self._numItemData % columnCount === 0 ? totalRowCnt : totalRowCnt + 1;
+ self._itemCount = columnCount;
+
+ if ( self._cellSize <= 0 ) {
+ return ;
}
- // Get template data
- if ( $el.data( "template" ) ) {
- o.template = $el.data( "template" );
+ rowsPerView = self._clipSize / self._cellSize;
+ rowsPerView = Math.ceil( rowsPerView );
+ self._rowsPerView = parseInt( rowsPerView, 10 );
+
+ $child = $( self._makeRows( rowsPerView + 2 ) );
+ self._$view.append( $child.children() );
+ self._$view.children().css( attributeName, self._cellSize + "px" );
+ self._$rows = self._$view.children().detach();
+
+ self._reservedPos = -self._cellSize;
+ self._scalableSize = -self._cellSize;
- /* to support swipe list, <li> or <ul> can be main node of virtual list. */
- if ( $el.data( "swipelist" ) == true ) {
- o.childSelector = " ul";
- } else {
- o.childSelector = " li";
- }
- }
+ self._initLayout();
- // Set data's unique key
- // NOTE: Unnecessary?
- if ( $el.data( "dbkey" ) ) {
- o.dbkey = $el.data( "dbkey" );
+ self._blockScroll = self._rowsPerView > self._totalRowCnt;
+ self._maxSizeExceptClip = ( self._totalRowCnt - self._rowsPerView ) * self._cellSize;
+ self._maxSize = self._totalRowCnt * self._cellSize;
+ self._maxViewSize = ( self._rowsPerView ) * self._cellSize;
+ self._modifyViewPos = -self._cellSize;
+ if ( self._clipSize < self._maxViewSize ) {
+ self._modifyViewPos = ( -self._cellSize ) + ( self._clipSize - self._maxViewSize );
}
-
- t._first_index = 0; // initial top idx of <li> element.
- t._last_index = o.row - 1; // initial bottom idx of <li> element.
- t._initList(); // NOTE: Called at here only!
},
- destroy : function () {
- var o = this.options;
-
- $( document ).unbind( "scrollstop" );
+ _getinheritedSize : function ( elem ) {
+ var $target = $( elem ),
+ height,
+ width,
+ NODETYPE = { ELEMENT_NODE : 1, TEXT_NODE : 3 },
+ ret = {
+ isDefinedWidth : false,
+ isDefinedHeight : false,
+ width : 0,
+ height : 0
+ };
- $( window ).off( "throttledresize", this._resize );
+ while ( $target[0].nodeType === NODETYPE.ELEMENT_NODE && ( ret.isDefinedWidth === false || ret.isHeightDefined === false ) ) {
+ height = $target[0].style.height;
+ width = $target[0].style.width;
- $( o.id ).empty();
+ if ( ret.isDefinedHeight === false && height !== "" ) {
+ // Size was defined
+ ret.isDefinedHeight = true;
+ ret.height = parseInt( height, 10 );
+ }
- if ( this.timerMoveID ) {
- clearTimeout( this.timerMoveID );
- this.timerMoveID = null;
+ if ( ret.isDefinedWidth === false && width !== "" ) {
+ // Size was defined
+ ret.isDefinedWidth = true;
+ ret.width = parseInt( width, 10 );
+ }
+ $target = $target.parent();
+ if ( $target.hasClass( "ui-content" ) ) {
+ break;
+ }
}
+ return ret;
},
- _itemApply: function ( $list, item ) {
- var $countli = item.find( ".ui-li-count" );
+ _resize : function () {
+ var self = this,
+ ret = null,
+ rowsPerView = 0,
+ itemCount = 0,
+ totalRowCnt = 0,
+ diffRowCnt = 0,
+ clipSize = 0,
+ prevcnt = 0,
+ clipPosition = 0,
+ rowsLength = 0,
+ row = null,
+ size = 0;
- if ( $countli.length ) {
- item.addClass( "ui-li-has-count" );
+ if ( self._direction ) {
+ size = self._calculateClipHeight();
+ self._$view.height( size );
+ self._$clip.height( size );
+ } else {
+ size = self._calculateClipWidth();
+ self._$view.width( size );
+ self._$clip.width( size );
}
- $countli.addClass( "ui-btn-up-" + ( $list.jqmData( "counttheme" ) || this.options.countTheme ) + " ui-btn-corner-all" );
+ itemCount = self._calculateColumnCount();
+ if ( itemCount != self._itemCount ) {
+ totalRowCnt = parseInt( self._numItemData / itemCount, 10 );
+ self._totalRowCnt = self._numItemData % itemCount === 0 ? totalRowCnt : totalRowCnt + 1;
+ prevcnt = self._itemCount;
+ self._itemCount = itemCount;
+ clipPosition = self._getClipPosition();
+ self._$view.hide();
- // TODO class has to be defined in markup
- item.find( "h1, h2, h3, h4, h5, h6" ).addClass( "ui-li-heading" ).end()
- .find( "p, dl" ).addClass( "ui-li-desc" ).end()
- .find( ">img:eq(0), .ui-link-inherit>img:eq(0)" ).addClass( "ui-li-thumb" ).each( function () {
- item.addClass( $( this ).is( ".ui-li-icon" ) ? "ui-li-has-icon" : "ui-li-has-thumb" );
- }).end()
- .find( ".ui-li-aside" ).each(function () {
- var $this = $( this );
- $this.prependTo( $this.parent() ); //shift aside to front for css float
- } );
- },
+ diffRowCnt = self._replaceRows( itemCount, prevcnt, self._totalRowCnt, clipPosition );
+ self._maxSizeExceptClip = ( self._totalRowCnt - self._rowsPerView ) * self._cellSize;
+ self._maxSize = self._totalRowCnt * self._cellSize;
+ self._scalableSize += ( -diffRowCnt ) * self._cellSize;
+ self._reservedPos += ( -diffRowCnt ) * self._cellSize;
+ self._setScrollBarSize();
+ self._setScrollBarPosition( diffRowCnt );
- _removeCorners: function ( li, which ) {
- var top = "ui-corner-top ui-corner-tr ui-corner-tl",
- bot = "ui-corner-bottom ui-corner-br ui-corner-bl";
+ self._$view.show();
+ }
- li = li.add( li.find( ".ui-btn-inner, .ui-li-link-alt, .ui-li-thumb" ) );
+ clipSize = self._calculateClipSize();
+ if ( clipSize !== self._clipSize ) {
+ rowsPerView = clipSize / self._cellSize;
+ rowsPerView = parseInt( Math.ceil( rowsPerView ), 10 );
- if ( which === "top" ) {
- li.removeClass( top );
- } else if ( which === "bottom" ) {
- li.removeClass( bot );
- } else {
- li.removeClass( top + " " + bot );
+ if ( rowsPerView > self._rowsPerView ) {
+ // increase row.
+ self._increaseRow( rowsPerView - self._rowsPerView );
+ } else if ( rowsPerView < self._rowsPerView ) {
+ // decrease row.
+ self._decreaseRow( self._rowsPerView - rowsPerView );
+ }
+ self._$rows = self._$view.children();
+ self._$rows.sort( function ( a, b ) {
+ return a.getAttribute( "row-index" ) - b.getAttribute( "row-index" );
+ });
+
+ self._rowsPerView = rowsPerView;
+ self._clipSize = clipSize;
+ self._blockScroll = self._rowsPerView > self._totalRowCnt;
+ self._maxSizeExceptClip = ( self._totalRowCnt - self._rowsPerView ) * self._cellSize;
+ self._maxSize = self._totalRowCnt * self._cellSize;
+ self._maxViewSize = ( self._rowsPerView ) * self._cellSize;
+ if ( self._clipSize < self._maxViewSize ) {
+ self._modifyViewPos = ( -self._cellSize ) + ( self._clipSize - self._maxViewSize );
+ }
+ if ( self._direction ) {
+ self._$clip.width( self._clipSize );
+ } else {
+ self._$clip.height( self._clipSize );
+ }
+ self._setScrollBarSize();
+ self._setScrollBarPosition( 0 );
+ self._setViewSize();
}
},
- _refreshCorners: function ( create ) {
- var $li,
- $visibleli,
- $topli,
- $bottomli;
-
- if ( this.options.inset ) {
- $li = this.element.children( "li" );
- // at create time the li are not visible yet so we need to rely on .ui-screen-hidden
- $visibleli = create ? $li.not( ".ui-screen-hidden" ) : $li.filter( ":visible" );
+ resize : function () {
+ var self = this,
+ height = 0,
+ $virtualgrid = $( ".ui-virtualgrid-view" );
- this._removeCorners( $li );
+ self._inheritedSize = self._getinheritedSize( self.element );
- // Select the first visible li element
- $topli = $visibleli.first()
- .addClass( "ui-corner-top" );
+ if ( $virtualgrid.length !== 0 ) {
+ self._resize();
+ }
+ },
- $topli.add( $topli.find( ".ui-btn-inner" ) )
- .find( ".ui-li-link-alt" )
- .addClass( "ui-corner-tr" )
- .end()
- .find( ".ui-li-thumb" )
- .not( ".ui-li-icon" )
- .addClass( "ui-corner-tl" );
+ _initScrollView : function () {
+ var self = this,
+ oldDirection = self.options.direction;
+ $.extend( self.options, self._scrollView.options );
+ self.options.direction = oldDirection;
+ self.options.moveThreshold = 10;
+ self.options.showScrollBars = false;
+ self._getScrollHierarchy = self._scrollView._getScrollHierarchy;
+ self._makePositioned = self._scrollView._makePositioned;
+ self._set_scrollbar_size = self._scrollView._set_scrollbar_size;
+ self._setStyleTransform = self._scrollView._setElementTransform;
+ self._hideOverflowIndicator = self._scrollView._hideOverflowIndicator;
+ self._showOverflowIndicator = self._scrollView._showOverflowIndicator;
+ self._setGestureScroll = self._scrollView._setGestureScroll;
+ },
- // Select the last visible li element
- $bottomli = $visibleli.last()
- .addClass( "ui-corner-bottom" );
+ _createTracker : function () {
+ var self = this;
- $bottomli.add( $bottomli.find( ".ui-btn-inner" ) )
- .find( ".ui-li-link-alt" )
- .addClass( "ui-corner-br" )
- .end()
- .find( ".ui-li-thumb" )
- .not( ".ui-li-icon" )
- .addClass( "ui-corner-bl" );
+ self._tracker = new MomentumTracker( self.options );
+ if ( self._direction ) {
+ self._hTracker = self._tracker;
+ self._$clip.width( self._clipSize );
+ } else {
+ self._vTracker = self._tracker;
+ self._$clip.height( self._clipSize );
}
},
- // this virtuallistview object
- refresh: function ( create ) {
- this.parentPage = this.element.closest( ".ui-page" );
- // Make sub page, and move the virtuallist into it...
- // NOTE: check this subroutine.
- this._createSubPages();
-
- var o = this.options,
- $list = this.element,
- self = this,
- dividertheme = $list.jqmData( "dividertheme" ) || o.dividerTheme,
- listsplittheme = $list.jqmData( "splittheme" ),
- listspliticon = $list.jqmData( "spliticon" ),
- li = $list.children( "li" ),
- counter = $.support.cssPseudoElement || !$.nodeName( $list[ 0 ], "ol" ) ? 0 : 1,
- item,
- itemClass,
- temTheme,
- a,
- last,
- splittheme,
- countParent,
- icon,
- pos,
- numli,
- itemTheme;
+ //----------------------------------------------------//
+ // Overflow effect
+ //----------------------------------------------------//
+ _createOverflowArea : function () {
+ var self = this,
+ prefix = "<div class=\"ui-virtualgrid-overflow-indicator-",
+ suffixTop = "-top\"></div>",
+ suffixBottom = "-bottom\"></div>";
- // TODO: ?
- if ( counter ) {
- $list.find( ".ui-li-dec" ).remove();
+ if ( self.options.rotation ) {
+ return;
}
- for ( pos = 0, numli = li.length; pos < numli; pos++ ) {
- item = li.eq( pos );
- itemClass = "ui-li";
-
- // If we're creating the element, we update it regardless
- if ( create || !item.hasClass( "ui-li" ) ) {
- itemTheme = item.jqmData( "theme" ) || o.theme;
- a = item.children( "a" );
-
- if ( a.length ) {
- icon = item.jqmData( "icon" );
+ if ( self._direction ) {
+ self._overflowTop = $( prefix + "x" + suffixTop );
+ self._overflowBottom = $( prefix + "x" + suffixBottom );
+ } else {
+ self._overflowTop = $( prefix + "y" + suffixTop );
+ self._overflowBottom = $( prefix + "y" + suffixBottom );
+ }
- item.buttonMarkup({
- wrapperEls: "div",
- shadow: false,
- corners: false,
- iconpos: "right",
- /* icon: a.length > 1 || icon === false ? false : icon || "arrow-r",*/
- icon: false, /* Remove unnecessary arrow icon */
- theme: itemTheme
- });
+ self._$clip.append( self._overflowTop );
+ self._$clip.append( self._overflowBottom );
+ self._overflowDisplayed = false;
+ },
- if ( ( icon != false ) && ( a.length == 1 ) ) {
- item.addClass( "ui-li-has-arrow" );
- }
+ _hideVGOverflowIndicator : function () {
+ if ( this._overflowDisplayed === false ) {
+ return;
+ }
- a.first().addClass( "ui-link-inherit" );
+ this._overflowTop.animate( { opacity: 0 }, 300 );
+ this._overflowBottom.animate( { opacity: 0 }, 300 );
+ this._overflowDisplayed = false;
+ },
- if ( a.length > 1 ) {
- itemClass += " ui-li-has-alt";
+ //----------------------------------------------------//
+ // Scrollbar //
+ //----------------------------------------------------//
+ _createScrollBar : function () {
+ var self = this,
+ prefix = "<div class=\"ui-scrollbar ui-scrollbar-",
+ suffix = "\"><div class=\"ui-scrollbar-track\"><div class=\"ui-scrollbar-thumb\"></div></div></div>";
- last = a.last();
- splittheme = listsplittheme || last.jqmData( "theme" ) || o.splitTheme;
+ if ( self.options.rotation ) {
+ return ;
+ }
- last.appendTo(item)
- .attr( "title", last.getEncodedText() )
- .addClass( "ui-li-link-alt" )
- .empty()
- .buttonMarkup({
- shadow: false,
- corners: false,
- theme: itemTheme,
- icon: false,
- iconpos: false
- })
- .find( ".ui-btn-inner" )
- .append(
- $( "<span />" ).buttonMarkup({
- shadow: true,
- corners: true,
- theme: splittheme,
- iconpos: "notext",
- icon: listspliticon || last.jqmData( "icon" ) || o.splitIcon
- })
- );
- }
- } else if ( item.jqmData( "role" ) === "list-divider" ) {
+ if ( self._direction ) {
+ self._$clip.append( prefix + "x" + suffix );
+ self._hScrollBar = self._$clip.children( ".ui-scrollbar-x" );
+ self._hScrollBar.find( ".ui-scrollbar-thumb" ).addClass( "ui-scrollbar-thumb-x" );
+ } else {
+ self._$clip.append( prefix + "y" + suffix );
+ self._vScrollBar = self._$clip.children( ".ui-scrollbar-y" );
+ self._vScrollBar.find( ".ui-scrollbar-thumb" ).addClass( "ui-scrollbar-thumb-y" );
+ }
+ },
- itemClass += " ui-li-divider ui-btn ui-bar-" + dividertheme;
- item.attr( "role", "heading" );
+ _setScrollBarSize: function () {
+ var self = this,
+ scrollBarSize = 0,
+ currentSize = 0,
+ $scrollBar,
+ attrName,
+ className;
- //reset counter when a divider heading is encountered
- if ( counter ) {
- counter = 1;
- }
+ if ( self.options.rotation ) {
+ return ;
+ }
- } else {
- itemClass += " ui-li-static ui-body-" + itemTheme;
- }
- }
+ scrollBarSize = parseInt( self._maxViewSize / self._clipSize, 10 );
+ if ( self._direction ) {
+ $scrollBar = self._hScrollBar.find( ".ui-scrollbar-thumb" );
+ attrName = "width";
+ currentSize = $scrollBar.width();
+ className = "ui-scrollbar-thumb-x";
+ self._hScrollBar.css( "width", self._clipSize );
+ } else {
+ $scrollBar = self._vScrollBar.find( ".ui-scrollbar-thumb" );
+ attrName = "height";
+ className = "ui-scrollbar-thumb-y";
+ currentSize = $scrollBar.height();
+ self._vScrollBar.css( "height", self._clipSize );
+ }
- if ( counter && itemClass.indexOf( "ui-li-divider" ) < 0 ) {
- countParent = item.is( ".ui-li-static:first" ) ? item : item.find( ".ui-link-inherit" );
+ if ( scrollBarSize > currentSize ) {
+ $scrollBar.removeClass( className );
+ $scrollBar.css( attrName, scrollBarSize );
+ } else {
+ scrollBarSize = currentSize;
+ }
- countParent.addClass( "ui-li-jsnumbering" )
- .prepend( "<span class='ui-li-dec'>" + (counter++) + ". </span>" );
- }
+ self._itemScrollSize = parseFloat( ( self._clipSize - scrollBarSize ) / ( self._totalRowCnt - self._rowsPerView ) );
+ self._itemScrollSize = Math.round( self._itemScrollSize * 100 ) / 100;
+ },
- item.add( item.children( ".ui-btn-inner" ) ).addClass( itemClass );
+ _setScrollBarPosition : function ( di, duration ) {
+ var self = this,
+ $sbt = null,
+ x = "0px",
+ y = "0px",
+ translate;
- self._itemApply( $list, item );
+ if ( self.options.rotation ) {
+ return ;
}
- this._refreshCorners( create );
+ self._currentItemCount = self._currentItemCount + di;
+ if ( self._vScrollBar ) {
+ $sbt = self._vScrollBar.find( ".ui-scrollbar-thumb" );
+ y = ( self._currentItemCount * self._itemScrollSize ) + "px";
+ } else {
+ $sbt = self._hScrollBar.find( ".ui-scrollbar-thumb" );
+ x = ( self._currentItemCount * self._itemScrollSize ) + "px";
+ }
+ self._setStyleTransform( $sbt, x, y, duration );
},
- //create a string for ID/subpage url creation
- _idStringEscape: function ( str ) {
- return str.replace(/\W/g , "-");
+ _hideScrollBars : function () {
+ var self = this,
+ vclass = "ui-scrollbar-visible";
+
+ if ( self.options.rotation ) {
+ return ;
+ }
+
+ if ( self._vScrollBar ) {
+ self._vScrollBar.removeClass( vclass );
+ } else {
+ self._hScrollBar.removeClass( vclass );
+ }
},
- // ?
- // this virtuallistview object
- _createSubPages: function () {
- var parentList = this.element,
- parentPage = parentList.closest( ".ui-page" ),
- parentUrl = parentPage.jqmData( "url" ),
- parentId = parentUrl || parentPage[ 0 ][ $.expando ],
- parentListId = parentList.attr( "id" ),
- o = this.options,
- dns = "data-" + $.mobile.ns,
- self = this,
- persistentFooterID = parentPage.find( ":jqmData(role='footer')" ).jqmData( "id" ),
- hasSubPages,
- newRemove;
+ _showScrollBars : function () {
+ var self = this,
+ vclass = "ui-scrollbar-visible";
- if ( typeof listCountPerPage[ parentId ] === "undefined" ) {
- listCountPerPage[ parentId ] = -1;
+ if ( self.options.rotation ) {
+ return ;
}
- parentListId = parentListId || ++listCountPerPage[ parentId ];
+ if ( self._vScrollBar ) {
+ self._vScrollBar.addClass( vclass );
+ } else {
+ self._hScrollBar.addClass( vclass );
+ }
+ },
- $( parentList.find( "li>ul, li>ol" ).toArray().reverse() ).each(function ( i ) {
- var self = this,
- list = $( this ),
- listId = list.attr( "id" ) || parentListId + "-" + i,
- parent = list.parent(),
- nodeEls,
- title = nodeEls.first().getEncodedText(),//url limits to first 30 chars of text
- id = ( parentUrl || "" ) + "&" + $.mobile.subPageUrlKey + "=" + listId,
- theme = list.jqmData( "theme" ) || o.theme,
- countTheme = list.jqmData( "counttheme" ) || parentList.jqmData( "counttheme" ) || o.countTheme,
- newPage,
- anchor;
+ //----------------------------------------------------//
+ // scroll process //
+ //----------------------------------------------------//
+ centerTo : function ( selector ) {
+ var self = this,
+ row = null,
+ targetItem = null,
+ targetRowIndex = -1,
+ rowsLength = self._$rows.length,
+ newPosition,
+ i;
- nodeEls = $( list.prevAll().toArray().reverse() );
- nodeEls = nodeEls.length ? nodeEls : $( "<span>" + $.trim( parent.contents()[ 0 ].nodeValue ) + "</span>" );
+ if ( !self.options.rotation ) {
+ return;
+ }
- //define hasSubPages for use in later removal
- hasSubPages = true;
+ for ( i = 0; i < rowsLength; ++i ) {
+ row = $( self._$rows[ i ] );
+ targetItem = row.children( "." + selector );
+ if ( targetItem.length ) {
+ targetRowIndex = parseInt( row.attr( "row-index" ), 10 );
+ break;
+ }
+ }
- newPage = list.detach()
- .wrap( "<div " + dns + "role='page' " + dns + "url='" + id + "' " + dns + "theme='" + theme + "' " + dns + "count-theme='" + countTheme + "'><div " + dns + "role='content'></div></div>" )
- .parent()
- .before( "<div " + dns + "role='header' " + dns + "theme='" + o.headerTheme + "'><div class='ui-title'>" + title + "</div></div>" )
- .after( persistentFooterID ? $( "<div " + dns + "role='footer' " + dns + "id='" + persistentFooterID + "'>" ) : "" )
- .parent()
- .appendTo( $.mobile.pageContainer );
+ if ( targetRowIndex === -1 ) {
+ targetRowIndex = self._getTargetRowIndex( selector );
+ if ( targetRowIndex === -1 ) {
+ return;
+ }
+ }
- newPage.page();
+ newPosition = -( targetRowIndex * self._cellSize - ( self._clipSize - self._cellSize ) / 2 );
+ if ( self._direction ) {
+ self.scrollTo( newPosition, 0 );
+ } else {
+ self.scrollTo( 0, newPosition );
+ }
+ },
- anchor = parent.find('a:first');
+ _getTargetRowIndex: function ( selector ) {
+ var self = this,
+ dataCount = self._numItemData,
+ itemCount = self._itemCount,
+ attrName = self._direction ? "top" : "left",
+ html = "",
+ targetRowIndex = self._totalRowCnt,
+ i;
- if ( !anchor.length ) {
- anchor = $( "<a/>" ).html( nodeEls || title ).prependTo( parent.empty() );
+ for ( i = 0; i < dataCount; ++i ) {
+ html = self._makeHtmlData( i, i % itemCount, attrName );
+ if ( self._hasClassItem( html, selector ) ) {
+ targetRowIndex = parseInt( i / itemCount, 10 );
+ break;
}
+ }
- anchor.attr( "href", "#" + id );
-
- }).virtuallistview();
-
- // on pagehide, remove any nested pages along with the parent page, as long as they aren't active
- // and aren't embedded
- if ( hasSubPages &&
- parentPage.is( ":jqmData(external-page='true')" ) &&
- parentPage.data( "page" ).options.domCache === false ) {
+ if ( targetRowIndex === self._totalRowCnt ) {
+ return -1;
+ }
- newRemove = function ( e, ui ) {
- var nextPage = ui.nextPage, npURL;
+ return targetRowIndex;
+ },
- if ( ui.nextPage ) {
- npURL = nextPage.jqmData( "url" );
- if ( npURL.indexOf( parentUrl + "&" + $.mobile.subPageUrlKey ) !== 0 ) {
- self.childPages().remove();
- parentPage.remove();
- }
- }
- };
+ _hasClassItem: function ( html, selector ) {
+ var self = this,
+ classString = self._getItemClass( html );
- // unbind the original page remove and replace with our specialized version
- parentPage
- .unbind( "pagehide.remove" )
- .bind( "pagehide.remove", newRemove );
+ if ( classString.indexOf( selector ) === -1 ) {
+ return false;
}
- },
- // TODO sort out a better way to track sub pages of the virtuallistview this is brittle
- childPages: function () {
- var parentUrl = this.parentPage.jqmData( "url" );
+ if ( classString.indexOf( "virtualgrid-item" ) === -1 ) {
+ return false;
+ }
- return $( ":jqmData(url^='" + parentUrl + "&" + $.mobile.subPageUrlKey + "')" );
- }
- });
+ return true;
+ },
- //auto self-init widgets
- $( document ).bind( "pagecreate create", function ( e ) {
- $( $.tizen.virtuallistview.prototype.options.initSelector, e.target ).virtuallistview();
- });
+ _getItemClass: function ( html ) {
+ var classIndex = html.indexOf( "class" ),
+ classBeginIndex = Math.min( html.indexOf( "\"", classIndex ), html.indexOf( "'", classIndex ) ),
+ classEndIndex = Math.min( html.indexOf( "\"", classBeginIndex + 1 ), html.indexOf( "'", classBeginIndex + 1 ) );
-} ( jQuery ) );
+ return html.slice( classBeginIndex + 1, classEndIndex );
+ },
+ scrollTo: function ( x, y, duration ) {
+ var self = this;
+ if ( self._direction ) {
+ x -= self._cellSize;
+ self._sx = self._reservedPos;
+ self._reservedPos = x;
+ } else {
+ y -= self._cellSize;
+ self._sy = self._reservedPos;
+ self._reservedPos = y;
+ }
+ self._scrollView.scrollTo.apply( this, [ x, y, duration ] );
+ },
+ getScrollPosition: function () {
+ if ( this.direction ) {
+ return { x: -this._ry, y: 0 };
+ }
+ return { x: 0, y: -this._ry };
+ },
-/**
- * @class core
- * loader.js
- *
- * Youmin Ha <youmin.ha@samsung.com>
- *
- *
- */
-/*
- Web UI scaling concept in Tizen Web UI
+ _setScrollPosition: function ( x, y ) {
+ var self = this,
+ sy = self._scalableSize,
+ distance = self._direction ? x : y,
+ dy = distance - sy,
+ di = parseInt( dy / self._cellSize, 10 ),
+ i = 0,
+ idx = 0,
+ replaceStartIdx = 0,
+ realRowCount = self._rowsPerView + 2,
+ rawView = self._$view[0];
-Generally, web applications must be designed to be showed acceptable on various size and resolution of screens, and web winsets have to be scaled well. Tizen Web UI Framework supports various viewport settings, and Tizen Web UI widgets are designed to be scalable on various screen sizes. In order to make web applications scalable on many devices which have different screen size, it is necessary to understand how mobile web browsers deal with screen resolution, and how Tizen Web UI Framework supports scaling for web applications.
+ if ( self._blockScroll ) {
+ if ( dy > 0 && distance >= -self._cellSize && self._scalableSize >= -self._cellSize ) {
+ self._overflowDir = _OVERFLOW_DIR_UP;
+ }
+ if ( dy < 0 && self._scalableSize <= -( self._maxSizeExceptClip + self._cellSize ) ) {
+ self._overflowDir = _OVERFLOW_DIR_DOWN;
+ }
+ return;
+ }
+ if ( ! self.options.rotation ) {
+ if ( dy > 0 && distance >= -self._cellSize && self._scalableSize >= -self._cellSize ) {
+ // top
+ self._stopMScroll();
+ self._scalableSize = -self._cellSize;
+ self._setElementTransform( -self._cellSize );
+ if ( self._overflowDir === _OVERFLOW_DIR_NONE ) {
+ self._overflowDir = _OVERFLOW_DIR_UP;
+ }
+ return;
+ }
+ if ( dy < 0 && self._scalableSize <= -( self._maxSizeExceptClip + self._cellSize ) ) {
+ // bottom
+ self._stopMScroll();
+ self._scalableSize = -( self._maxSizeExceptClip + self._cellSize );
+ self._setElementTransform( self._modifyViewPos );
+ if ( self._overflowDir === _OVERFLOW_DIR_NONE ) {
+ self._overflowDir = _OVERFLOW_DIR_DOWN;
+ }
+ return;
+ }
+ }
-* Viewport on mobile web browser
+ replaceStartIdx = ( Math.abs( di ) < realRowCount ) ? 0 : ( di > 0 ) ? di - realRowCount : di + realRowCount;
+ if ( di > 0 ) { // scroll up
+ for ( i = replaceStartIdx; i < di; ++i ) {
+ idx = -parseInt( ( sy / self._cellSize ) + i + 3, 10 );
+ self._replaceRow( rawView.lastChild, circularNum( idx, self._totalRowCnt ) );
+ rawView.insertBefore( rawView.lastChild, rawView.firstChild );
+ }
+ } else if ( di < 0 ) { // scroll down
+ for ( i = replaceStartIdx; i > di; --i ) {
+ idx = self._rowsPerView - parseInt( ( sy / self._cellSize ) + i, 10 );
+ self._replaceRow( rawView.firstChild, circularNum( idx, self._totalRowCnt ) );
+ rawView.insertBefore( rawView.firstChild, rawView.lastChild.nextSibling );
+ }
+ }
+ self._setScrollBarPosition( -di );
+ self._scalableSize += di * self._cellSize;
+ self._setElementTransform( distance - self._scalableSize - self._cellSize );
+ },
-Viewport is an area showing web content on the browser. Unlike desktop browsers, mobile browsers support logical viewport seting, which means that application can set viewport width/height and zoom level by itself.
-The very important thing that to be remembered is that the viewport resolution in pixel is 'Logical', not physical. For example, if the viewport width is set to 480 on a mobile device having 720px screen width, the viewport width is considered to 480px logically. All elements put on right side from 480px horizontal position will not be shown on the viewport.
-Most mobile browsers set viewport with given content attribute with <meta name="viewport" content="..."> tag in <head> section in the application source html, whereas desktop browsers ignore the tag.
-Detailed usage of viewport meta tag is found in here: http://www.w3.org/TR/mwabp/#bp-viewport
+ _setElementTransform : function ( value ) {
+ var self = this,
+ x = 0,
+ y = 0;
+ if ( self._direction ) {
+ x = value + "px";
+ } else {
+ y = value + "px";
+ }
+ self._setStyleTransform( self._$view, x, y );
+ },
-* Viewport setting by application developers
+ //----------------------------------------------------//
+ // Event handler //
+ //----------------------------------------------------//
+ _handleMomentumScroll: function () {
+ var self = this,
+ opts = self.options,
+ keepGoing = false,
+ v = this._$view,
+ x = 0,
+ y = 0,
+ t = self._tracker;
-When developers write <meta name="viewport" content="..."> in the <head> section of the web application HTML file, Tizen Web UI Framework does not add another viewport meta tag, nor modify developer-defined viewport.
+ if ( t ) {
+ t.update();
+ if ( self._direction ) {
+ x = t.getPosition();
+ } else {
+ y = t.getPosition();
+ }
+ keepGoing = !t.done();
+ }
+ self._setScrollPosition( x, y );
+ if ( !opts.rotation ) {
+ keepGoing = !t.done();
+ self._reservedPos = self._direction ? x : y;
+ // bottom
+ self._reservedPos = self._reservedPos <= (-(self._maxSizeExceptClip - self._modifyViewPos)) ? ( - ( self._maxSizeExceptClip + self._cellSize) ) : self._reservedPos;
+ // top
+ self._reservedPos = self._reservedPos > -self._cellSize ? -self._cellSize : self._reservedPos;
+ } else {
+ self._reservedPos = self._direction ? x : y;
+ }
+ self._$clip.trigger( self.options.updateEventName, [ { x: x, y: y } ] );
-* Automatic viewport setting by Tizen Web UI Framework
+ if ( keepGoing ) {
+ self._timerID = setTimeout( self._timerCB, self._timerInterval );
+ } else {
+ self._stopMScroll();
+ }
+ },
-If developers do not give a viewport meta tag, Tizen Web UI Framework automatically add a viewport meta tag with default viewport setting.
+ _startMScroll: function ( speedX, speedY ) {
+ var self = this;
+ if ( self._direction ) {
+ self._sx = self._reservedPos;
+ } else {
+ self._sy = self._reservedPos;
+ }
+ self._scrollView._startMScroll.apply( self, [ speedX, speedY ] );
+ },
+ _stopMScroll: function () {
+ this._scrollView._stopMScroll.apply( this );
+ },
-* Portrait/landscape mode
+ _enableTracking: function () {
+ var self = this;
+ self._$view.bind( self._dragMoveEvt, self._dragMoveCB );
+ self._$view.bind( self._dragStopEvt, self._dragStopCB );
+ self._scrollView._enableTracking.apply( self );
+ },
+ _disableTracking: function () {
+ var self = this;
+ self._$view.unbind( self._dragMoveEvt, self._dragMoveCB );
+ self._$view.unbind( self._dragStopEvt, self._dragStopCB );
+ self._scrollView._disableTracking.apply( self );
+ },
-* Tizen Web UI widgets scaling
+ _handleDragStart: function ( e, ex, ey ) {
+ var self = this;
+ self._scrollView._handleDragStart.apply( this, [ e, ex, ey ] );
+ self._eventPos = self._direction ? ex : ey;
+ self._nextPos = self._reservedPos;
+ },
+ _handleDragMove: function ( e, ex, ey ) {
+ var self = this,
+ dx = ex - self._lastX,
+ dy = ey - self._lastY,
+ x = 0,
+ y = 0,
+ diffFromStartPos = 0,
+ diffFromLastPos = 0,
+ opacity = 0,
+ overflowPos = 0,
+ overFlowTarget = null;
- */
-( function ($, Globalize, window, undefined) {
+ self._lastMove = getCurrentTime();
+ self._speedX = dx;
+ self._speedY = dy;
- var tizen = {
- libFileName : "tizen-web-ui-fw(.min)?.js",
+ self._didDrag = true;
- frameworkData : {
- rootDir: '/usr/lib/tizen-web-ui-fw',
- version: '0.1',
- theme: "tizen-white",
- viewportWidth: "device-width",
- viewportScale: false,
+ self._lastX = ex;
+ self._lastY = ey;
- defaultFontSize: 22,
- minified: false,
+ if ( self._direction ) {
+ self._movePos = ex - self._eventPos;
+ x = self._nextPos + self._movePos;
+ overflowPos = ex;
+ } else {
+ self._movePos = ey - self._eventPos;
+ y = self._nextPos + self._movePos;
+ overflowPos = ey;
+ }
+ self._showScrollBars();
+ self._setScrollPosition( x, y );
+ if ( self._overflowDir !== _OVERFLOW_DIR_NONE ) {
+ overFlowTarget = ( self._overflowDir === _OVERFLOW_DIR_UP ) ? self._overflowTop : self._overflowBottom;
+ if ( !self._overflowDisplayed ) {
+ self._overflowDisplayed = true;
+ self._overflowStartPos = overflowPos;
+ }
+ diffFromStartPos = ( overflowPos - self._overflowStartPos ) * self._overflowDir;
+ opacity = ( diffFromStartPos < 0 ) ?
+ 0 : ( diffFromStartPos > self._overflowMaxDragDist ) ?
+ 1 : ( diffFromStartPos / self._overflowMaxDragDist );
+ overFlowTarget.css( "opacity", opacity );
+ }
- debug: false
+ return false;
},
- log : {
- debug : function ( msg ) {
- if ( tizen.frameworkData.debug ) {
- console.log( msg );
- }
- },
- warn : function ( msg ) {
- console.warn( msg );
- },
- error : function ( msg ) {
- console.error( msg );
- },
- alert : function ( msg ) {
- window.alert( msg );
+ _handleDragStop: function ( e ) {
+ var self = this;
+
+ self._reservedPos = self._movePos ? self._nextPos + self._movePos : self._reservedPos;
+ self._scrollView._handleDragStop.apply( this, [ e ] );
+ if ( self._overflowDir !== _OVERFLOW_DIR_NONE ) {
+ self._overflowDir = _OVERFLOW_DIR_NONE;
+ self._hideVGOverflowIndicator();
}
+ return self._didDrag ? false : undefined;
},
- util : {
+ _addBehaviors: function () {
+ var self = this;
- loadScriptSync : function ( scriptPath, successCB, errorCB ) {
- $.ajax( {
- url: scriptPath,
- dataType: 'script',
- async: false,
- crossDomain: false,
- success: successCB,
- error: function ( jqXHR, textStatus, errorThrown ) {
- if ( errorCB ) {
- errorCB( jqXHR, textStatus, errorThrown );
- } else {
- var ignoreStatusList = [ 404 ], // 404: not found
- errmsg = ( 'Error while loading ' + scriptPath + '\n' + jqXHR.status + ':' + jqXHR.statusText );
- if ( -1 == $.inArray( jqXHR.status, ignoreStatusList ) ) {
- tizen.log.alert( errmsg );
- } else {
- tizen.log.warn( errmsg );
- }
- }
- }
+ // scroll event handler.
+ if ( self.options.eventType === "mouse" ) {
+ self._dragStartEvt = "mousedown";
+ self._dragStartCB = function ( e ) {
+ return self._handleDragStart( e, e.clientX, e.clientY );
+ };
+
+ self._dragMoveEvt = "mousemove";
+ self._dragMoveCB = function ( e ) {
+ return self._handleDragMove( e, e.clientX, e.clientY );
+ };
+
+ self._dragStopEvt = "mouseup";
+ self._dragStopCB = function ( e ) {
+ return self._handleDragStop( e, e.clientX, e.clientY );
+ };
+
+ self._$view.bind( "vclick", function ( e ) {
+ return !self._didDrag;
} );
- },
- isMobileBrowser: function ( ) {
- var mobileIdx = window.navigator.appVersion.indexOf("Mobile"),
- isMobile = -1 < mobileIdx;
- return isMobile;
- }
- },
+ } else { //touch
+ self._dragStartEvt = "touchstart";
+ self._dragStartCB = function ( e ) {
+ var t = e.originalEvent.targetTouches[0];
+ return self._handleDragStart( e, t.pageX, t.pageY );
+ };
- css : {
- cacheBust: ( document.location.href.match( /debug=true/ ) ) ?
- '?cacheBust=' + ( new Date( ) ).getTime( ) :
- '',
- addElementToHead : function ( elem ) {
- var head = document.getElementsByTagName( 'head' )[0];
- if ( head ) {
- $( head ).prepend( elem );
- }
- },
- makeLink : function ( href ) {
- var cssLink = document.createElement( 'link' );
- cssLink.setAttribute( 'rel', 'stylesheet' );
- cssLink.setAttribute( 'href', href );
- cssLink.setAttribute( 'name', 'tizen-theme' );
- return cssLink;
- },
- load: function ( path ) {
- var head = document.getElementsByTagName( 'head' )[0],
- cssLinks = head.getElementsByTagName( 'link' ),
- idx,
- l = null;
- // Find css link element
- for ( idx = 0; idx < cssLinks.length; idx++ ) {
- if ( cssLinks[idx].getAttribute( 'rel' ) != "stylesheet" ) {
- continue;
- }
- if ( cssLinks[idx].getAttribute( 'name' ) == "tizen-theme"
- || cssLinks[idx].getAttribute( 'href' ) == path ) {
- l = cssLinks[idx];
- break;
- }
- }
- if ( l ) { // Found the link element!
- if ( l.getAttribute( 'href' ) == path ) {
- tizen.log.warn( "Theme is already loaded. Skip theme loading in the framework." );
- } else {
- l.setAttribute( 'href', path );
- }
- } else {
- this.addElementToHead( this.makeLink( path ) );
- }
+ self._dragMoveEvt = "touchmove";
+ self._dragMoveCB = function ( e ) {
+ var t = e.originalEvent.targetTouches[0];
+ return self._handleDragMove( e, t.pageX, t.pageY );
+ };
+
+ self._dragStopEvt = "touchend";
+ self._dragStopCB = function ( e ) {
+ return self._handleDragStop( e );
+ };
}
- },
+ self._$view.bind( self._dragStartEvt, self._dragStartCB );
- getParams: function ( ) {
- /* Get data-* params from <script> tag, and set tizen.frameworkData.* values
- * Returns true if proper <script> tag is found, or false if not.
- */
- // Find current <script> tag element
- var scriptElems = document.getElementsByTagName( 'script' ),
- val = null,
- foundScriptTag = false,
- idx,
- elem,
- src,
- tokens,
- version_idx;
+ // other events.
+ self._$view.delegate( ".virtualgrid-item", "click", function ( event ) {
+ var $selectedItem = $( this );
+ $selectedItem.trigger( "select", this );
+ } );
- function getTizenTheme( ) {
- var t = navigator.theme ? navigator.theme.split( ':' )[0] : null;
- if ( t ) {
- t = t.replace('-hd', '');
- if ( ! t.match( /^tizen-/ ) ) {
- t = 'tizen-' + t;
- }
+ $( window ).bind( "resize", function ( e ) {
+ var height = 0,
+ $virtualgrid = $( ".ui-virtualgrid-view" );
+ if ( $virtualgrid.length !== 0 ) {
+ self._resize();
}
- return t;
- }
+ } );
- for ( idx in scriptElems ) {
- elem = scriptElems[idx];
- src = elem.src ? elem.getAttribute( 'src' ) : undefined;
- if (src && src.match( this.libFileName )) {
- // Set framework data, only when they are given.
- tokens = src.split(/[\/\\]/);
- version_idx = -3;
- this.frameworkData.rootDir = ( elem.getAttribute( 'data-framework-root' )
- || tokens.slice( 0, tokens.length + version_idx ).join( '/' )
- || this.frameworkData.rootDir ).replace( /^file:(\/\/)?/, '' );
- this.frameworkData.version = elem.getAttribute( 'data-framework-version' )
- || tokens[ tokens.length + version_idx ]
- || this.frameworkData.version;
- this.frameworkData.theme = elem.getAttribute( 'data-framework-theme' )
- || getTizenTheme( )
- || this.frameworkData.theme;
- this.frameworkData.viewportWidth = elem.getAttribute( 'data-framework-viewport-width' )
- || this.frameworkData.viewportWidth;
- this.frameworkData.viewportScale =
- "true" === elem.getAttribute( 'data-framework-viewport-scale' ) ? true
- : this.frameworkData.viewportScale;
- this.frameworkData.minified = src.search(/\.min\.js$/) > -1 ? true : false;
- this.frameworkData.debug = "true" === elem.getAttribute( 'data-framework-debug' ) ? true
- : this.frameworkData.debug;
- foundScriptTag = true;
- break;
+ $( document ).one( "pageshow", function ( event ) {
+ var $page = $( self.element ).parents( ".ui-page" ),
+ $header = $page.find( ":jqmData(role='header')" ),
+ $footer = $page.find( ":jqmData(role='footer')" ),
+ $content = $page.find( ":jqmData(role='content')" ),
+ footerHeight = $footer ? $footer.height() : 0,
+ headerHeight = $header ? $header.height() : 0;
+
+ if ( $page && $content ) {
+ $content.height( window.innerHeight - headerHeight - footerHeight ).css( "overflow", "hidden" );
+ $content.addClass( "ui-virtualgrid-content" );
}
- }
- return foundScriptTag;
+ } );
},
- loadTheme: function ( theme ) {
- var themePath,
- cssPath,
- jsPath;
+ //----------------------------------------------------//
+ // Calculate size about dom element. //
+ //----------------------------------------------------//
+ _calculateClipSize : function () {
+ var self = this,
+ clipSize = 0;
- if ( ! theme ) {
- theme = tizen.frameworkData.theme;
- }
-
- themePath = tizen.frameworkData.rootDir + '/' + tizen.frameworkData.version + '/themes/' + theme;
-
- jsPath = themePath + '/theme.js';
-
- if ( tizen.frameworkData.minified ) {
- cssPath = themePath + '/tizen-web-ui-fw-theme.min.css';
+ if ( self._direction ) {
+ clipSize = self._calculateClipWidth();
} else {
- cssPath = themePath + '/tizen-web-ui-fw-theme.css';
+ clipSize = self._calculateClipHeight();
}
- tizen.css.load( cssPath );
- tizen.util.loadScriptSync( jsPath );
+ return clipSize;
},
- /** Load Globalize culture file, and set default culture.
- * @param[in] language (optional) Language code. ex) en-US, en, ko-KR, ko
- * If language is not given, read language from html 'lang' attribute,
- * or from system setting.
- * @param[in] cultureDic (optional) Dictionary having language code->
- */
- loadGlobalizeCulture: function ( language, cultureDic ) {
+ _calculateClipWidth : function () {
var self = this,
- cFPath,
- lang,
- mockJSXHR;
+ $parent = self._$clip.parent(),
+ paddingValue = 0,
+ clipSize = $( window ).width();
- function getLang ( language ) {
- var lang = language
- || $( 'html' ).attr( 'lang' )
- || window.navigator.language.split( '.' )[0] // Webkit, Safari + workaround for Tizen
- || window.navigator.userLanguage // IE
- || 'en',
- countryCode = null,
- countryCodeIdx = lang.lastIndexOf('-'),
- ignoreCodes = ['Cyrl', 'Latn', 'Mong']; // Not country code!
- if ( countryCodeIdx != -1 ) { // Found country code!
- countryCode = lang.substr( countryCodeIdx + 1 );
- if ( ignoreCodes.join( '-' ).indexOf( countryCode ) < 0 ) {
- // countryCode is not found from ignoreCodes.
- // Make countryCode to uppercase.
- lang = [ lang.substr( 0, countryCodeIdx ), countryCode.toUpperCase( ) ].join( '-' );
- }
- }
- // NOTE: 'en' to 'en-US', because globalize has no 'en' culture file.
- lang = lang == 'en' ? 'en-US' : lang;
- return lang;
+ if ( self._inheritedSize.isDefinedWidth ) {
+ return self._inheritedSize.width;
}
- function getNeutralLang ( lang ) {
- var neutralLangIdx = lang.lastIndexOf( '-' ),
- neutralLang;
- if ( neutralLangIdx != -1 ) {
- neutralLang = lang.substr( 0, neutralLangIdx );
- }
- return neutralLang;
+ if ( $parent.hasClass( "ui-content" ) ) {
+ paddingValue = parseInt( $parent.css( "padding-left" ), 10 );
+ clipSize = clipSize - ( paddingValue || 0 );
+ paddingValue = parseInt( $parent.css( "padding-right" ), 10 );
+ clipSize = clipSize - ( paddingValue || 0 );
+ } else {
+ clipSize = self._$clip.width();
}
+ return clipSize;
+ },
- function getCultureFilePath ( lang, cFDic ) {
- var cFPath = null; // error value
+ _calculateClipHeight : function () {
+ var self = this,
+ $parent = self._$clip.parent(),
+ header = null,
+ footer = null,
+ paddingValue = 0,
+ clipSize = $( window ).height();
- if ( "string" != typeof lang ) {
- return null;
- }
- if ( cFDic && cFDic[lang] ) {
- cFPath = cFDic[lang];
- } else {
- // Default Globalize culture file path
- cFPath = [
- self.frameworkData.rootDir,
- self.frameworkData.version,
- 'js',
- 'cultures',
- ['globalize.culture.', lang, '.js'].join( '' )
- ].join( '/' );
- }
- return cFPath;
+ if ( self._inheritedSize.isDefinedHeight ) {
+ return self._inheritedSize.height;
}
- function printLoadError( cFPath, jqXHR ) {
- tizen.log.error( "Error " + jqXHR.status + ": " + jqXHR.statusText
- + "::Culture file (" + cFPath + ") is failed to load.");
- }
+ if ( $parent.hasClass( "ui-content" ) ) {
+ paddingValue = parseInt( $parent.css( "padding-top" ), 10 );
+ clipSize = clipSize - ( paddingValue || 0 );
+ paddingValue = parseInt( $parent.css( "padding-bottom" ), 10 );
+ clipSize = clipSize - ( paddingValue || 0 );
+ header = $parent.siblings( ".ui-header" );
+ footer = $parent.siblings( ".ui-footer" );
- function loadCultureFile ( cFPath, errCB ) {
- function _successCB ( ) {
- tizen.log.debug( "Culture file (" + cFPath + ") is loaded successfully." );
- }
- function _errCB ( jqXHR, textStatus, err ) {
- if ( errCB ) {
- errCB( jqXHR, textStatus, err );
+ if ( header ) {
+ if ( header.outerHeight( true ) === null ) {
+ clipSize = clipSize - ( $( ".ui-header" ).outerHeight() || 0 );
} else {
- printLoadError( cFPath, jqXHR );
+ clipSize = clipSize - header.outerHeight( true );
}
}
-
- if ( ! cFPath ) { // Invalid cFPath -> Regard it as '404 Not Found' error.
- mockJSXHR = {
- status: 404,
- statusText: "Not Found"
- };
- _errCB( mockJSXHR, null, null );
- } else {
- $.ajax( {
- url: cFPath,
- dataType: 'script',
- cache: true,
- async: false,
- success: _successCB,
- error: _errCB
- } );
+ if ( footer ) {
+ clipSize = clipSize - footer.outerHeight( true );
}
+ } else {
+ clipSize = self._$clip.height();
}
-
- lang = getLang( language );
- cFPath = getCultureFilePath( lang, cultureDic );
- loadCultureFile( cFPath,
- function ( jqXHR, textStatus, err ) {
- if ( jqXHR.status == 404 ) {
- // If culture file is not found, try once more with neutral lang.
- var nLang = getNeutralLang( lang ),
- ncFPath = getCultureFilePath( nLang, cultureDic );
- loadCultureFile( ncFPath, null );
- } else {
- printLoadError( cFPath, jqXHR );
- }
- } );
-
- return lang;
- },
- setGlobalize: function ( ) {
- var lang = this.loadGlobalizeCulture( );
-
- // Set culture
- // NOTE: It is not needed to set with neutral lang.
- // Globalize automatically deals with it.
- Globalize.culture( lang );
- },
- /**
- * Load custom globalize culture file
- * Find current system language, and load appropriate culture file from given colture file list.
- *
- * @param[in] cultureDic collection of 'language':'culture file path' key-val pair.
- * @example
- * var myCultures = {
- * "en" : "culture/en.js",
- * "fr" : "culture/fr.js",
- * "ko-KR" : "culture/ko-KR.js"
- * };
- * loadCultomGlobalizeCulture( myCultures );
- *
- * ex) culture/fr.js
- * -------------------------------
- * Globalize.addCultureInfo( "fr", {
- * messages: {
- * "hello" : "bonjour",
- * "translate" : "traduire"
- * }
- * } );
- * -------------------------------
- */
- loadCustomGlobalizeCulture: function ( cultureDic ) {
- tizen.loadGlobalizeCulture( null, cultureDic );
+ return clipSize;
},
- /** Set viewport meta tag for mobile devices.
- *
- * @param[in] viewportWidth viewport width. "device-width" is OK.
- */
- setViewport: function ( viewportWidth ) {
- var meta = null,
- head,
- content;
+ _calculateColumnSize : function () {
+ var self = this,
+ $tempBlock,
+ $cell;
- // Do nothing if viewport setting code is already in the code.
- $( "meta[name=viewport]" ).each( function ( ) {
- meta = this;
- return;
- });
- if ( meta ) { // Found custom viewport!
- content = $( meta ).prop( "content" );
- viewportWidth = content.replace( /.*width=(device-width|\d+)\s*,?.*$/gi, "$1" );
- tizen.log.warn( "Viewport is set to '" + viewportWidth + "' in a meta tag. Framework skips viewport setting." );
+ $tempBlock = $( self._makeRows( 1 ) );
+ self._$view.append( $tempBlock.children().first() );
+ if ( self._direction ) {
+ // x-axis
+ self._viewSize = self._$view.width();
+ $cell = self._$view.children().first().children().first();
+ self._cellSize = $cell.outerWidth( true );
+ self._cellOtherSize = $cell.outerHeight( true );
} else {
- // Create a meta tag
- meta = document.createElement( "meta" );
- if ( meta ) {
- meta.name = "viewport";
- content = "width=" + viewportWidth + ", user-scalable=no";
- if ( ! isNaN( viewportWidth ) ) {
- // Fix scale to 1.0, if viewport width is set to fixed value.
- // NOTE: Works wrong in Tizen browser!
- //content = [ content, ", initial-scale=1.0, maximum-scale=1.0" ].join( "" );
- }
- meta.content = content;
- tizen.log.debug( content );
- head = document.getElementsByTagName( 'head' ).item( 0 );
- head.insertBefore( meta, head.firstChild );
- }
+ // y-axis
+ self._viewSize = self._$view.height();
+ $cell = self._$view.children().first().children().first();
+ self._cellSize = $cell.outerHeight( true );
+ self._cellOtherSize = $cell.outerWidth( true );
}
- return viewportWidth;
+ $tempBlock.remove();
+ self._$view.children().remove();
},
- /** Read body's font-size, scale it, and reset it.
- * param[in] desired font-size / base font-size.
- */
- scaleBaseFontSize: function ( themeDefaultFontSize, ratio ) {
- tizen.log.debug( "themedefaultfont size: " + themeDefaultFontSize + ", ratio: " + ratio );
- var scaledFontSize = Math.max( Math.floor( themeDefaultFontSize * ratio ), 4 );
+ _calculateColumnCount : function ( ) {
+ var self = this,
+ $view = self._$clip,
+ viewSize = self._direction ? $view.innerHeight() : $view.innerWidth(),
+ itemCount = 0 ;
- $( 'html' ).css( { 'font-size': scaledFontSize + "px" } );
- tizen.log.debug( 'html:font size is set to ' + scaledFontSize );
- $( document ).ready( function ( ) {
- $( '.ui-mobile' ).children( 'body' ).css( { 'font-size': scaledFontSize + "px" } );
- } );
- },
+ if ( self._direction ) {
+ viewSize = viewSize - ( parseInt( $view.css( "padding-top" ), 10 ) + parseInt( $view.css( "padding-bottom" ), 10 ) );
+ } else {
+ viewSize = viewSize - ( parseInt( $view.css( "padding-left" ), 10 ) + parseInt( $view.css( "padding-right" ), 10 ) );
+ }
- setScaling: function ( ) {
- var viewportWidth = this.frameworkData.viewportWidth,
- themeDefaultFontSize = this.frameworkData.defaultFontSize, // comes from theme.js
- ratio = 1;
+ itemCount = parseInt( ( viewSize / self._cellOtherSize ), 10 );
+ return itemCount > 0 ? itemCount : 1 ;
+ },
- // Keep original font size
- $( 'body' ).attr( 'data-tizen-theme-default-font-size', themeDefaultFontSize );
+ // Read the position of clip form property ('webkit-transform').
+ // @return : number - position of clip.
+ _getClipPosition : function () {
+ var self = this,
+ matrix = null,
+ contents = null,
+ result = -self._cellSize,
+ $scrollview = self._$view.closest( ".ui-scrollview-view" );
- if ( !tizen.util.isMobileBrowser() ) {
- return;
+ if ( $scrollview ) {
+ matrix = $scrollview.css( "-webkit-transform" );
+ contents = matrix.substr( 7 );
+ contents = contents.substr( 0, contents.length - 1 );
+ contents = contents.split( ', ' );
+ result = Math.abs( contents [5] );
}
+ return result;
+ },
- // Legacy support: tizen.frameworkData.viewportScale
- if ( this.frameworkData.viewportScale == true ) {
- viewportWidth = "screen-width";
- }
+ //----------------------------------------------------//
+ // DOM Element handle //
+ //----------------------------------------------------//
+ _makeRows : function ( count ) {
+ var self = this,
+ index = 0,
+ row = null,
+ wrapper = null;
- // screen-width support
- if ( "screen-width" == viewportWidth ) {
- if ( window.self == window.top ) {
- // Top frame: for target. Use window.outerWidth.
- viewportWidth = window.outerWidth;
- } else {
- // iframe: for web simulator. Use clientWidth.
- viewportWidth = document.documentElement.clientWidth;
+ wrapper = self._createElement( "div" );
+ wrapper.setAttribute( "class", "ui-scrollview-view" );
+ for ( index = 0; index < count ; index += 1 ) {
+ row = self._makeRow( index );
+ if ( self._direction ) {
+ row.style.top = 0;
+ row.style.left = index * self._cellSize;
}
+ wrapper.appendChild( row );
}
+ return wrapper;
+ },
- // set viewport meta tag
- viewportWidth = this.setViewport( viewportWidth ); // If custom viewport setting exists, get viewport width
+ // make a single row block
+ _makeRow : function ( rowIndex ) {
+ var self = this,
+ index = rowIndex * self._itemCount,
+ colIndex = 0,
+ blockClassName = self._direction ? "ui-virtualgrid-wrapblock-x" : "ui-virtualgrid-wrapblock-y",
+ wrapBlock = self._createElement( "div" ),
+ strWrapInner = "",
+ attrName = self._direction ? "top" : "left";
- if ( viewportWidth == "device-width" ) {
- // Do nothing!
- } else { // fixed width!
- ratio = parseFloat( viewportWidth / this.frameworkData.defaultViewportWidth );
- this.scaleBaseFontSize( themeDefaultFontSize, ratio );
+ for ( colIndex = 0; colIndex < self._itemCount; colIndex++ ) {
+ strWrapInner += self._makeHtmlData( index, colIndex, attrName );
+ index += 1;
}
- }
- };
-
- function export2TizenNS ( $, tizen ) {
- if ( !$.tizen ) {
- $.tizen = { };
- }
+ wrapBlock.innerHTML = strWrapInner;
+ wrapBlock.setAttribute( "class", blockClassName );
+ wrapBlock.setAttribute( "row-index", String( rowIndex ) );
+ self._fragment.appendChild( wrapBlock );
+ return wrapBlock;
+ },
- $.tizen.frameworkData = tizen.frameworkData;
- $.tizen.loadCustomGlobalizeCulture = tizen.loadCustomGlobalizeCulture;
- $.tizen.loadTheme = tizen.loadTheme;
+ _makeHtmlData : function ( dataIndex, colIndex, attrName ) {
+ var self = this,
+ htmlStr = "",
+ itemData = null;
- $.tizen.__tizen__ = tizen; // for unit-test
- }
+ itemData = self._itemData( dataIndex );
+ if ( itemData ) {
+ htmlStr = self._getConvertedTmplStr( itemData );
+ htmlStr = self._insertPosToTmplStr( htmlStr, attrName, ( colIndex * self._cellOtherSize ) );
+ }
- export2TizenNS( $, tizen );
+ return htmlStr;
+ },
- tizen.getParams( );
- tizen.loadTheme( );
- tizen.setScaling( ); // Run after loadTheme(), for the default font size.
- tizen.setGlobalize( );
- // Turn off JQM's auto initialization option.
- // NOTE: This job must be done before domready.
- $.mobile.autoInitializePage = false;
+ _insertPosToTmplStr : function ( tmplStr, attrName, posVal ) {
+ var tagCloseIdx = tmplStr.indexOf( '>' ),
+ classIdx = -1,
+ firstPart,
+ lastPart,
+ result,
+ found = false,
+ targetIdx = 0,
+ firstPartLen,
+ i = 0;
- $(document).ready( function ( ) {
- $.mobile.initializePage( );
- });
+ if ( tagCloseIdx === -1 ) {
+ return;
+ }
-} ( jQuery, window.Globalize, window ) );
+ firstPart = tmplStr.slice( 0, tagCloseIdx );
+ lastPart = tmplStr.slice( tagCloseIdx, tmplStr.length );
+ classIdx = firstPart.indexOf( 'class' );
+ if ( classIdx !== -1 ) {
+ firstPartLen = firstPart.length;
+ for ( i = classIdx + 6; i < firstPartLen; i++ ) {
+ if ( firstPart.charAt( i ) === "\"" || firstPart.charAt( i ) === "\'" ) {
+ if ( found === false ) {
+ found = true;
+ } else {
+ targetIdx = i;
+ break;
+ }
+ }
+ }
+ result = firstPart.slice( 0, targetIdx ) + " virtualgrid-item" + firstPart.slice( targetIdx, firstPartLen ) + lastPart;
+ } else {
+ result = firstPart + " class=\"virtualgrid-item\"" + lastPart;
+ }
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Author: Minkyu Kang <mk7.kang@samsung.com>
- */
+ if ( !isNaN( posVal ) ) {
+ result = result.replace( '>', " style=\"" + attrName + ": " + String( posVal ) + "px\">");
+ }
-/*
- * Notification widget
- *
- * HTML Attributes
- *
- * data-role: set to 'notification'.
- * data-type: 'ticker' or 'popup'.
- * data-interval: time to showing. If don't set, will show infinitely.
- *
- * APIs
- *
- * open(): open the notification.
- * close(): close the notification.
- * text(text0, text1): set texts or get texts
- * icon(src): set the icon (tickernoti only)
- *
- * Events
- *
- * N/A
- *
- * Examples
- *
- * // tickernoti
- * <div data-role="notification" id="notification" data-type="ticker" data-interval="3000">
- * <img src="icon01.png">
- * <p>Hello World</p>
- * <p>Denis</p>
- * </div>
- *
- * // smallpopup
- * <div data-role="notification" id="notification" data-type="popup" data-interval="3000">
- * <p>Hello World</p>
- * </div>
- *
- */
+ return result;
+ },
-/**
- @class Notification
- The notification widget shows a pop-up window on the screen to provide notifications.
- To add a notification widget to the application, use the following code:
+ _increaseRow : function ( num ) {
+ var self = this,
+ rotation = self.options.rotation,
+ totalRowCnt = self._totalRowCnt,
+ rowView = self._$view[ 0 ],
+ firstRow = null,
+ lastRow = rowView.lastChild,
+ row = null,
+ headRowIndex = 0,
+ tailRowIndex = 0,
+ i;
- <div data-role="page">
- <div data-role="notification" data-type="smallpopup">
- <p>text1</p>
- </div>
- <div data-role="header"></div>
- <div data-role="content"></div>
- <div data-role="footer"></div>
- </div>
-*/
-/**
- @property {String} data-type
- Defines the notification type. The type options are tickernoti and smallpopup. <br/>The default value is smallpopup.
+ if ( !lastRow ) {
+ return;
+ }
-*/
-/**
- @property {Integer} data-interval
- Defines the time to showing a notification widget. <br/>The default is infinitely.
+ tailRowIndex = parseInt( lastRow.getAttribute( "row-index" ), 10 );
+ if ( !rotation ) {
+ firstRow = rowView.firstChild;
+ headRowIndex = parseInt( firstRow.getAttribute( "row-index" ), 10 );
+ }
-*/
-/**
- @method open
- The open method is used to open the notification widget:
+ for ( i = 0 ; i < num ; ++i ) {
+ if ( tailRowIndex >= totalRowCnt - 1 && !rotation ) {
+ if ( headRowIndex == 0 ) {
+ break;
+ }
- <div data-role="notification" data-type="smallpopup" data-interval="3000"></div>
- $('#notification').notification('open');
-*/
-/**
- @method close
- The close method is used to close the notification widget:
+ row = self._makeRow( --headRowIndex );
+ rowView.insertBefore( row, firstRow );
+ firstRow = row;
+ } else {
+ row = self._makeRow( circularNum( ++tailRowIndex, totalRowCnt ) );
+ rowView.appendChild( row );
+ }
- <div data-role="notification" data-type="smallpopup" data-interval="3000"></div>
- $('#notification').notification('close');
-*/
-/**
- @method text
- The text method is used to set or get the notification text:
+ if ( self._direction ) {
+ $( row ).width( self._cellSize );
+ } else {
+ $( row ).height( self._cellSize );
+ }
+ }
+ },
- <div data-role="notification" data-type="smallpopup" data-interval="3000"></div>
- // Set notification text
- $('#notification').notification('text', 'setThisText');
- // Get notification text
- texts = $('#notification').notification('text');
- @since Tizen2.0
-*/
-/**
- @method icon
- The setIcon method is used to set the ticker notification icon. The icon can be set only if the notification type is set to tickernoti.
+ _decreaseRow : function ( num ) {
+ var self = this,
+ rowView = self._$view[ 0 ],
+ i;
- <div data-role="notification" data-type="ticker" data-interval="3000"></div>
- $('#notification').notification('icon', './test.png');
-*/
-(function ( $, window ) {
- $.widget( "tizen.notification", $.mobile.widget, {
- btn: null,
- text_bg: [],
- icon_img: [],
- interval: null,
- seconds: null,
- running: false,
+ for ( i = 0 ; i < num ; ++i ) {
+ rowView.removeChild( rowView.lastChild );
+ }
+ },
- _get_text: function () {
- var text = new Array( 2 );
+ _replaceRows : function ( curCnt, prevCnt, maxCnt, clipPosition ) {
+ var self = this,
+ $rows = self._$view.children(),
+ prevRowIndex = 0,
+ rowIndex = 0,
+ diffRowCnt = 0,
+ targetCnt = 1,
+ filterCondition = ( self._filterRatio * self._cellSize ) + self._cellSize,
+ idx = 0;
- if ( this.type === 'ticker' ) {
- text[0] = $( this.text_bg[0] ).text();
- text[1] = $( this.text_bg[1] ).text();
+ if ( filterCondition < clipPosition ) {
+ targetCnt += 1;
+ }
+
+ prevRowIndex = parseInt( $( $rows[targetCnt] ).attr( "row-index" ), 10 );
+ if ( prevRowIndex === 0 ) {
+ // only top.
+ rowIndex = maxCnt - targetCnt;
} else {
- text[0] = $( this.text_bg[0] ).text();
+ rowIndex = Math.round( ( prevRowIndex * prevCnt ) / curCnt );
+ if ( rowIndex + self._rowsPerView >= maxCnt ) {
+ // only bottom.
+ rowIndex = maxCnt - self._rowsPerView;
+ }
+ diffRowCnt = prevRowIndex - rowIndex;
+ rowIndex -= targetCnt;
}
- return text;
+ for ( idx = 0 ; idx < $rows.length ; idx += 1 ) {
+ self._replaceRow( $rows[idx], circularNum( rowIndex, self._totalRowCnt ) );
+ rowIndex++;
+ }
+ return -diffRowCnt;
},
- _set_text: function ( text0, text1 ) {
- var _set = function ( elem, text ) {
- if ( !text ) {
- return;
- }
- elem.text( text );
- };
+ _replaceRow : function ( block, index ) {
+ var self = this,
+ tempBlocks = null;
- if ( this.type === 'ticker' ) {
- _set( $( this.text_bg[0] ), text0 );
- _set( $( this.text_bg[1] ), text1 );
- } else {
- _set( $( this.text_bg[0] ), text0 );
+ while ( block.hasChildNodes() ) {
+ block.removeChild( block.lastChild );
+ }
+
+ tempBlocks = self._makeRow( index );
+ while ( tempBlocks.children.length ) {
+ block.appendChild( tempBlocks.children[0] );
}
+ block.setAttribute( "row-index", tempBlocks.getAttribute( "row-index" ) );
+ tempBlocks.parentNode.removeChild( tempBlocks );
},
- text: function ( text0, text1 ) {
- if ( text0 === undefined && text1 === undefined ) {
- return this._get_text();
+ _createElement : function ( tag ) {
+ var element = document.createElement( tag );
+
+ this._fragment.appendChild( element );
+ return element;
+ },
+
+ _getObjectNames : function ( obj ) {
+ var properties = [],
+ name = "";
+
+ for ( name in obj ) {
+ properties.push( name );
}
+ this._properties = properties;
+ },
- this._set_text( text0, text1 );
+ _getConvertedTmplStr : function ( data ) {
+ var self = this,
+ dataProperties = self._properties,
+ i = 0,
+ plainMsg,
+ ret = "";
+
+ if ( !data ) {
+ return ;
+ }
+
+ plainMsg = self._templateText;
+ for ( i = 0; i < dataProperties.length; i++ ) {
+ plainMsg = self._strReplace( plainMsg, "${" + dataProperties[ i ] + "}" , data[ dataProperties[ i ] ] );
+ }
+ plainMsg = self._changeImgSrcAriaAttrFromTmpl( plainMsg );
+
+ return plainMsg;
},
- icon: function ( src ) {
- if ( src === undefined ) {
- return;
+ _changeImgSrcAriaAttrFromTmpl : function ( plainMsg ) {
+ var self = this,
+ ret = "",
+ targetTagIdx,
+ beforeTargetTag = "",
+ afterTargetTag = "",
+ imgFileName,
+ imgSrcSlashIdx,
+ temp,
+ srcRegExpResult;
+
+ temp = plainMsg;
+ targetTagIdx = temp.indexOf( "$ARIA-IMG-SRC-ALT$" );
+ while ( targetTagIdx !== -1 ) {
+ imgFileName = "";
+ beforeTargetTag = beforeTargetTag + temp.slice( 0, targetTagIdx + 19 );
+ afterTargetTag = temp.slice( targetTagIdx + 19, temp.length );
+ srcRegExpResult = afterTargetTag.match( imgTagSrcAttrRE );
+ if ( srcRegExpResult ) {
+ imgSrcSlashIdx = srcRegExpResult[0].lastIndexOf( "/" );
+ if ( imgSrcSlashIdx !== -1 ) {
+ imgFileName = srcRegExpResult[0].slice( imgSrcSlashIdx + 1, -1 );
+ }
+ }
+ beforeTargetTag = beforeTargetTag.replace( "$ARIA-IMG-SRC-ALT$", imgFileName );
+ temp = afterTargetTag;
+ targetTagIdx = temp.indexOf( "$ARIA-IMG-SRC-ALT$" );
+ ret = beforeTargetTag + afterTargetTag;
}
- this.icon_img.detach();
- this.icon_img = $( "<img src='" + src + "' class='ui-ticker-icon'>" );
- $( this.element ).find(".ui-ticker").append( this.icon_img );
+ if ( ret === "" ) {
+ ret = plainMsg;
+ }
+
+ return ret;
},
- _refresh: function () {
- var container = this._get_container();
+ _insertAriaAttrToTmpl : function ( plainMsg ) {
+ var ret = "",
+ targetTagIdx,
+ beforeTargetTag = "",
+ afterTargetTag = "",
+ temp;
+
+ temp = plainMsg.replace( "<div", "<div tabindex=\"0\" aria-selected=\"true\"" );
+ targetTagIdx = temp.indexOf( "<img" );
+ if ( targetTagIdx !== -1 ) {
+ while ( targetTagIdx !== -1 ) {
+ beforeTargetTag = beforeTargetTag + temp.slice( 0, targetTagIdx + 4 );
+ afterTargetTag = temp.slice( targetTagIdx + 4, temp.length );
+ beforeTargetTag = beforeTargetTag + " role=\"img\" alt=\"$ARIA-IMG-SRC-ALT$\"";
+ temp = afterTargetTag;
+ targetTagIdx = temp.indexOf( "<img" );
+ ret = beforeTargetTag + afterTargetTag;
+ }
+ temp = ret;
+ targetTagIdx = temp.indexOf( "<span" );
+ beforeTargetTag = "";
+ while ( targetTagIdx !== -1 ) {
+ beforeTargetTag = beforeTargetTag + temp.slice( 0, targetTagIdx + 5 );
+ afterTargetTag = temp.slice( targetTagIdx + 5, temp.length );
+ beforeTargetTag = beforeTargetTag + " aria-hidden=\"true\" tabindex=\"-1\"";
+ temp = afterTargetTag;
+ targetTagIdx = temp.indexOf( "<span" );
+ ret = beforeTargetTag + afterTargetTag;
+ }
+ }
- $( container ).addClass("fix")
- .removeClass("show")
- .removeClass("hide");
+ if ( ret === "" ) {
+ ret = plainMsg;
+ }
- this._set_interval();
+ return ret;
},
- open: function () {
- var container = this._get_container();
-
- if ( this.running ) {
- this._refresh();
- return;
+ _strReplace : function ( plainMsg, stringToFind, stringToReplace ) {
+ var temp = plainMsg,
+ index = plainMsg.indexOf( stringToFind );
+ while ( index !== -1 ) {
+ temp = temp.replace( stringToFind, stringToReplace );
+ index = temp.indexOf( stringToFind );
}
+ return temp;
+ }
- $( container ).addClass("show")
- .removeClass("hide")
- .removeClass("fix");
-
- this.running = true;
-
- if ( this.type === 'popup' ) {
- this._set_position();
- }
+ } );
- this._set_interval();
- },
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $( ":jqmData(role='virtualgrid')" ).virtualgrid();
+ } );
+} ( jQuery, window, document ) );
- close: function () {
- var container = this._get_container();
- if ( !this.running ) {
- return;
- }
- $( container ).addClass("hide")
- .removeClass("show")
- .removeClass("fix");
+/*
+ *
+ * This software is licensed under the MIT licence (as defined by the OSI at
+ * http://www.opensource.org/licenses/mit-license.php)
+ *
+ * ***************************************************************************
+ * Copyright (C) 2011 by Intel Corporation Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software" ),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ */
- this.running = false;
- clearInterval( this.interval );
- },
+// Base class for widgets that need the following features:
+//
+// I. HTML prototype loading
+//
+// This class provides HTML prototype loading for widgets. That is, the widget implementation specifies its HTML portions
+// in one continuous HTML snippet, and it optionally provides an object containing selectors into the various parts of the
+// HTML snippet. This widget loads the HTML snippet into a jQuery object, and optionally assigns jQuery objects to each of
+// the selectors in the optionally provided object.
+//
+// To use this functionality you can either derive from this class, or you can call its prototype's gtype method.
+//
+// 1. Widgets deriving from this class should define _htmlProto as part of their prototype declaration. _htmlProto looks like
+// this:
+//
+// _htmlProto: {
+// source: string|jQuery object (optional) default: string - The name of the widget
+// ui: {
+// uiElement1: "#ui-element-1-selector",
+// uiElement2: "#ui-element-2-selector",
+// ...
+// subElement: {
+// subElement1: "#sub-element-1-selector",
+// subElement2: "#sub-element-2-selector",
+// ...
+// }
+// ...
+// }
+// }
+//
+// If neither 'source' nor 'ui' are defined, you must still include an empty _htmlProto key (_htmlProto: {}) to indicate
+// that you wish to make use of this feature. This will cause a prototype HTML file named after your widget to be loaded.
+// The loaded prototype will be placed into your widget's prototype's _protoHtml.source key.
+//
+// If 'source' is defined as a string, it is the name of the widget (including namespace). This is the default. If your
+// widget's HTML prototype is loaded via AJAX and the name of the AJAX file is different from the name of your widget
+// (that is, it is not "<widgetName>.prototype.html", then you should explicitly define 'source' as:
+//
+// If you wish to load HTML prototypes via AJAX, modify the getProtoPath() function defined below to reflect the directory
+// structure holding your widget HTML prototypes.
+//
+// source: "alternateWidgetName"
+//
+// If AJAX loading fails, source is set to a jQuery object containing a div with an error message. You can check whether
+// loading failed via the jQuery object's jqmData( "tizen.widgetex.ajax.fail" ) data item. If false, then the jQuery object
+// is the actual prototype loaded via AJAX or present inline. Otherwise, the jQuery object is the error message div.
+//
+// If 'source' is defined as a jQuery object, it is considered already loaded.
+//
+// if 'ui' is defined inside _htmlProto, It is assumed to be an object such that every one of its keys is either a string,
+// or another object with the same properties as itself.
+//
+// When a widget is instantiated, the HTML prototype is loaded if not already present in the prototype. If 'ui' is present
+// inside _htmlProto, the prototype is cloned. Then, a new structure is created based on 'ui' with each selector replaced
+// by a jQuery object containing the results of performing .find() on the prototype's clone with the filter set to the
+// value of the string. In the special case where the selector starts with a '#', the ID is removed from the element after
+// it is assigned into the structure being created. This structure is then made accessible from the widget instance via
+// the '_ui' key (i.e., this._ui).
+//
+// 2. Use the loadPrototype method when your widget does not derive from $.tizen.widgetex:
+// Add _htmlProto to your widget's prototype as described above. Then, in your widget's _create() method, call
+// loadPrototype in the following manner:
+//
+// $.tizen.widgetex.loadPrototype.call(this, "namespace.widgetName" );
+//
+// Thereafter, you may use the HTML prototype from your widget's prototype or, if you have specified a 'ui' key in your
+// _htmlProto key, you may use this._ui from your widget instance.
+//
+// II. realize method
+//
+// When a widget is created, some of its properties cannot be set immediately, because they depend on the widths/heights
+// of its constituent elements. They can only be calculated when the page containing the widget is made visible via the
+// "pageshow" event, because widths/heights always evaluate to 0 when retrieved from a widget that is not visible. When
+// you inherit from widgetex, you can add a "_realize" function to your prototype. This function will be called once right
+// after _create() if the element that anchors your widget is on a visible page. Otherwise, it will be called when the
+// page to which the widget belongs emits the "pageshow" event.
+//
+// NB: If your widget is inside a container which is itself not visible, such as an expandable or a collapsible, your
+// widget will remain hidden even though "pageshow" is fired and therefore _realize is called. In this case, widths and
+// heights will be unreliable even during _realize.
+//
+// III. systematic option handling
+//
+// If a widget has lots of options, the _setOption function can become a long switch for setting each recognized option.
+// It is also tempting to allow options to determine the way a widget is created, by basing decisions on various options
+// during _create(). Often, the actions based on option values in _create() are the same as those in _setOption. To avoid
+// such code duplication, this class calls _setOption once for each option after _create() has completed.
+//
+// Furthermore, to avoid writing long switches in a widget's _setOption method, this class implements _setOption in such
+// a way that, for any given option (e.g. "myOption" ), _setOption looks for a method _setMyOption in the widget's
+// implementation, and if found, calls the method with the value of the option.
+//
+// If your widget does not inherit from widgetex, you can still use widgetex' systematic option handling:
+// 1. define the _setOption method for your widget as follows:
+// _setOption: $.tizen.widgetex.prototype._setOption
+// 2. Call this._setOptions(this.options) from your widget's _create() function.
+// 3. As with widgetex-derived widgets, implement a corresponding _setMyOptionName function for each option myOptionName
+// you wish to handle.
+//
+// IV. systematic value handling for input elements
+//
+// If your widget happens to be constructed from an <input> element, you have to handle the "value" attribute specially,
+// and you have to emit the "change" signal whenever it changes, in addition to your widget's normal signals and option
+// changes. With widgetex, you can assign one of your widget's "data-*" properties to be synchronized to the "value"
+// property whenever your widget is constructed onto an <input> element. To do this, define, in your prototype:
+//
+// _value: {
+// attr: "data-my-attribute",
+// signal: "signal-to-emit"
+// }
+//
+// Then, call this._setValue(newValue) whenever you wish to set the value for your widget. This will set the data-*
+// attribute, emit the custom signal (if set) with the new value as its parameter, and, if the widget is based on an
+// <input> element, it will also set the "value" attribute and emit the "change" signal.
+//
+// "attr" is required if you choose to define "_value", and identifies the data-attribute to set in addition to "value",
+// if your widget's element is an input.
+// "signal" is optional, and will be emitted when setting the data-attribute via this._setValue(newValue).
+//
+// If your widget does not derive from widgetex, you can still define "_value" as described above and call
+// $.tizen.widgetex.setValue(widget, newValue).
+//
+// V. Systematic enabled/disabled handling for input elements
+//
+// widgetex implements _setDisabled which will disable the input associated with this widget, if any. Thus, if you derive
+// from widgetex and you plan on implementing the disabled state, you should chain up to
+// $.tizen.widgetex.prototype._setDisabled(value), rather than $.Widget.prototype._setOption( "disabled", value).
- destroy: function () {
- var container = this._get_container();
+(function ($, undefined) {
- $( container ).removeClass("show")
- .removeClass("hide")
- .removeClass("fix");
+// Framework-specific HTML prototype path for AJAX loads
+ function getProtoPath() {
+ var theScriptTag = $( "script[data-framework-version][data-framework-root][data-framework-theme]" );
- this._del_event();
+ return (theScriptTag.attr( "data-framework-root" ) + "/" +
+ theScriptTag.attr( "data-framework-version" ) + "/themes/" +
+ theScriptTag.attr( "data-framework-theme" ) + "/proto-html" );
+ }
- this.running = false;
+ $.widget( "tizen.widgetex", $.mobile.widget, {
+ _createWidget: function () {
+ $.tizen.widgetex.loadPrototype.call( this, this.namespace + "." + this.widgetName );
+ $.mobile.widget.prototype._createWidget.apply( this, arguments );
},
- _get_container: function () {
- if ( this.type === 'ticker' ) {
- return $( this.element ).find(".ui-ticker");
+ _init: function () {
+ // TODO THIS IS TEMPORARY PATCH TO AVOID CTXPOPUP PAGE CRASH
+ if ( this.element === undefined ) {
+ return;
}
- return $( this.element ).find(".ui-smallpopup");
- },
+ var page = this.element.closest( ".ui-page" ),
+ self = this,
+ myOptions = {};
- _set_interval: function () {
- var self = this;
+ if ( page.is( ":visible" ) ) {
+ this._realize();
+ } else {
+ page.bind( "pageshow", function () { self._realize(); } );
+ }
- clearInterval( this.interval );
+ $.extend( myOptions, this.options );
- if ( this.seconds !== undefined && this.second !== 0 ) {
- this.interval = setInterval( function () {
- self.close();
- }, this.seconds );
- }
+ this.options = {};
+
+ this._setOptions( myOptions );
},
- _add_event: function () {
- var self = this,
- container = this._get_container();
+ _getCreateOptions: function () {
+ // if we're dealing with an <input> element, value takes precedence over corresponding data-* attribute, if a
+ // mapping has been established via this._value. So, assign the value to the data-* attribute, so that it may
+ // then be assigned to this.options in the superclass' _getCreateOptions
- if ( this.type === 'ticker' ) {
- container.find(".ui-ticker-btn").append( this.btn ).trigger("create");
+ if (this.element.is( "input" ) && this._value !== undefined) {
+ var theValue =
+ ( ( this.element.attr( "type" ) === "checkbox" || this.element.attr( "type" ) === "radio" )
+ ? this.element.is( ":checked" )
+ : this.element.is( "[value]" )
+ ? this.element.attr( "value" )
+ : undefined);
- this.btn.bind( "vmouseup", function () {
- self.close();
- });
+ if ( theValue != undefined ) {
+ this.element.attr( this._value.attr, theValue );
+ }
}
- container.bind( 'vmouseup', function () {
- self.close();
- });
+ return $.mobile.widget.prototype._getCreateOptions.apply( this, arguments );
},
- _del_event: function () {
- var container = this._get_container();
+ _setOption: function ( key, value ) {
+ var setter = "_set" + key.replace(/^[a-z]/, function (c) { return c.toUpperCase(); } );
- if ( this.type === 'ticker' ) {
- this.btn.unbind("vmouseup");
+ if ( this[setter] !== undefined ) {
+ this[setter]( value );
+ } else {
+ $.mobile.widget.prototype._setOption.apply( this, arguments );
}
- container.unbind('vmouseup');
- clearInterval( this.interval );
},
- _set_position: function () {
- var container = this._get_container(),
- $footer = $('.ui-page-active').children('.ui-footer'),
- footer_h = $footer.outerHeight() || 0;
+ _setDisabled: function ( value ) {
+ $.Widget.prototype._setOption.call( this, "disabled", value );
+ if ( this.element.is( "input" ) ) {
+ this.element.attr( "disabled", value );
+ }
+ },
- container.css( 'bottom', footer_h);
+ _setValue: function ( newValue ) {
+ $.tizen.widgetex.setValue( this, newValue );
},
- _create: function () {
- var self = this,
- elem = $( this.element ),
- i;
+ _realize: function () {}
+ } );
- this.btn = $('<div data-role="button" data-inline="true">Close</div>');
+ $.tizen.widgetex.setValue = function ( widget, newValue ) {
+ if ( widget._value !== undefined ) {
+ var valueString = ( widget._value.makeString ? widget._value.makeString(newValue) : newValue ),
+ inputType;
- this.seconds = elem.jqmData('interval');
- this.type = elem.jqmData('type') || 'popup';
+ widget.element.attr( widget._value.attr, valueString );
+ if ( widget._value.signal !== undefined ) {
+ widget.element.triggerHandler( widget._value.signal, newValue );
+ }
- if ( this.type === 'ticker' ) {
- elem.wrapInner("<div class='ui-ticker'></div>");
- elem.find(".ui-ticker").append("<div class='ui-ticker-body'></div>" +
- "<div class='ui-ticker-btn'></div>");
- this.text_bg = elem.find("p");
+ if ( widget.element.is( "input" ) ) {
+ inputType = widget.element.attr( "type" );
- if ( this.text_bg.length < 2 ) {
- elem.find(".ui-ticker").append("<p></p><p></p>");
- this.text_bg = elem.find("p");
- } else if ( this.text_bg.length > 2 ) {
- for ( i = 2; i < this.text_bg.length; i++ ) {
- $( this.text_bg[i] ).css( "display", "none" );
+ // Special handling for checkboxes and radio buttons, where the presence of the "checked" attribute is really
+ // the value
+ if ( inputType === "checkbox" || inputType === "radio" ) {
+ if ( newValue ) {
+ widget.element.attr( "checked", true );
+ } else {
+ widget.element.removeAttr( "checked" );
}
+ } else {
+ widget.element.attr( "value", valueString );
}
- $( this.text_bg[0] ).addClass("ui-ticker-text1-bg");
- $( this.text_bg[1] ).addClass("ui-ticker-text2-bg");
-
- this.icon_img = elem.find("img");
+ widget.element.trigger( "change" );
+ }
+ }
+ };
- if ( this.icon_img.length ) {
- $( this.icon_img ).addClass("ui-ticker-icon");
+ $.tizen.widgetex.assignElements = function (proto, obj) {
+ var ret = {},
+ key;
- for ( i = 1; i < this.icon_img.length; i++ ) {
- $( this.icon_img[i] ).css( "display", "none" );
- }
+ for ( key in obj ) {
+ if ( ( typeof obj[key] ) === "string" ) {
+ ret[key] = proto.find( obj[key] );
+ if ( obj[key].match(/^#/) ) {
+ ret[key].removeAttr( "id" );
}
} else {
- elem.wrapInner("<div class='ui-smallpopup'></div>");
- this.text_bg = elem.find("p").addClass("ui-smallpopup-text-bg");
-
- if ( this.text_bg.length < 1 ) {
- elem.find(".ui-smallpopup")
- .append("<p class='ui-smallpopup-text-bg'></p>");
- this.text_bg = elem.find("p");
- } else if ( this.text_bg.length > 1 ) {
- for ( i = 1; i < this.text_bg.length; i++ ) {
- $( this.text_bg[i] ).css( "display", "none" );
- }
+ if ( (typeof obj[key]) === "object" ) {
+ ret[key] = $.tizen.widgetex.assignElements( proto, obj[key] );
}
-
- this._set_position();
}
+ }
- this._add_event();
+ return ret;
+ };
- $( window ).bind( "resize", function () {
- if ( !self.running ) {
- return;
+ $.tizen.widgetex.loadPrototype = function ( widget, ui ) {
+ var ar = widget.split( "." ),
+ namespace,
+ widgetName,
+ source,
+ noSource = false,
+ htmlProto,
+ protoPath;
+
+ if ( ar.length == 2 ) {
+ namespace = ar[0];
+ widgetName = ar[1];
+
+ // If htmlProto is defined
+ if ( $[namespace][widgetName].prototype._htmlProto !== undefined ) {
+ // If no source is defined, use the widget name
+ source = $[namespace][widgetName].prototype._htmlProto.source;
+ if ( source === undefined ) {
+ source = widgetName;
+ noSource = true;
}
- self._refresh();
+ // Load the HTML prototype via AJAX if not defined inline
+ if ( typeof source === "string" ) {
+ if ( noSource ) { // use external htmlproto file
+ // Establish the path for the proto file
+ widget = source;
+ protoPath = getProtoPath();
- if ( self.type === 'popup' ) {
- self._set_position();
+ // Make the AJAX call
+ $.ajax( {
+ url: protoPath + "/" + widget + ".prototype.html",
+ async: false,
+ dataType: "html"
+ }).success( function (data, textStatus, jqXHR ) {
+ source = $( "<div></div>" ).html(data).jqmData( "tizen.widgetex.ajax.fail", false );
+ } );
+
+ // Assign the HTML proto to the widget prototype
+ source = $( "<div></div>" )
+ .text( "Failed to load proto for widget " + namespace + "." + widgetName + "!" )
+ .css( {background: "red", color: "blue", border: "1px solid black"} )
+ .jqmData( "tizen.widgetex.ajax.fail", true );
+
+ } else {
+ // inline definition (string)
+ source = $( source ).jqmData( "tizen.widgetex.ajax.fail", false );
+ }
+
+ } else {
+ // inline definition (object)
+ // AJAX loading has trivially succeeded, since there was no AJAX loading at all
+ source.jqmData( "tizen.widgetex.ajax.fail", false );
}
- });
- }
- }); // End of widget
+ htmlProto = source;
+ $[namespace][widgetName].prototype._htmlProto.source = source;
- // auto self-init widgets
- $( document ).bind( "pagecreate create", function ( e ) {
- $( e.target ).find(":jqmData(role='notification')").notification();
- });
+ // If there's a "ui" portion in the HTML proto, copy it over to this instance, and
+ // replace the selectors with the selected elements from a copy of the HTML prototype
+ if ( $[namespace][widgetName].prototype._htmlProto.ui !== undefined ) {
+ // Assign the relevant parts of the proto
+ $.extend( this, {
+ _ui: $.tizen.widgetex.assignElements( htmlProto.clone(), $[namespace][widgetName].prototype._htmlProto.ui )
+ });
+ }
+ }
+ }
+ };
- $( document ).bind( "pagebeforehide", function ( e ) {
- $( e.target ).find(":jqmData(role='notification')").notification('destroy');
- });
-}( jQuery, this ));
+}( jQuery ) );
-/*
- * jQuery Mobile Widget @VERSION
- *
- * This software is licensed under the MIT licence (as defined by the OSI at
- * http://www.opensource.org/licenses/mit-license.php)
- *
- * ***************************************************************************
+/* ***************************************************************************
* Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- * Copyright (c) 2011 by Intel Corporation Ltd.
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* DEALINGS IN THE SOFTWARE.
* ***************************************************************************
*
- * Authors: Max Waterman <max.waterman@intel.com>
- * Authors: Minkyu Kang <mk7.kang@samsung.com>
+ * Author: Wongi Lee <wongi11.lee@samsung.com>
+ * Youmin Ha <youmin.ha@samsung.com>
*/
/**
- * tizenslider modifies the JQuery Mobile slider and is created in the same way.
+ * Virtual List Widget for unlimited data.
+ * To support more then 1,000 items, special list widget developed.
+ * Fast initialize and light DOM tree.
+ * DB connection and works like DB cursor.
+ *
+ * HTML Attributes:
*
- * See the JQuery Mobile slider widget for more information :
- * http://jquerymobile.com/demos/1.0a4.1/docs/forms/forms-slider.html
+ * data-role: virtuallistview
+ * data-template : jQuery.template ID that populate into virtual list
+ * data-row : Optional. Set number of <li> elements that are used for data handling.
+ *
+ * ID : <UL> element that has "data-role=virtuallist" must have ID attribute.
*
- * The JQuery Mobile slider option:
- * theme: specify the theme using the 'data-theme' attribute
+ * * APIs:
*
- * Options:
- * theme: string; the theme to use if none is specified using the 'data-theme' attribute
- * default: 'c'
- * popup: boolean; controls whether the popup is displayed or not
- * specify if the popup is enabled using the 'data-popup' attribute
- * set from javascript using .tizenslider('option','popup',newValue)
+ * create ( {
+ * itemData: function ( idx ) { return json_obj; },
+ * numItemData: number or function () { return number; },
+ * cacheItemData: function ( minIdx, maxIdx ) {}
+ * } )
+ * : Create a virtuallist widget. At this moment, _create method is called.
+ * args : A collection of options
+ * itemData: A function that returns JSON object for given index. Mandatory.
+ * numItemData: Total number of itemData. Mandatory.
+ * cacheItemData: Virtuallist will ask itemData between minIdx and maxIdx.
+ * Developers can implement this function for preparing data.
+ * Optional.
*
* Events:
- * changed: triggers when the value is changed (rather than when the handle is moved)
+ *
+ * touchstart : Temporary preventDefault applied on touchstart event to avoid broken screen.
*
* Examples:
*
- * <a href="#" id="popupEnabler" data-role="button" data-inline="true">Enable popup</a>
- * <a href="#" id="popupDisabler" data-role="button" data-inline="true">Disable popup</a>
- * <div data-role="fieldcontain">
- * <input id="mySlider" data-theme='a' data-popup='false' type="range" name="slider" value="7" min="0" max="9" />
- * </div>
- * <div data-role="fieldcontain">
- * <input id="mySlider2" type="range" name="slider" value="77" min="0" max="777" />
- * </div>
+ * <script id="tmp-3-2-7" type="text/x-jquery-tmpl">
+ * <li class="ui-li-3-2-7">
+ * <span class="ui-li-text-main">${NAME}</span>
+ * <img src="00_winset_icon_favorite_on.png" class="ui-li-icon-sub">
+ * <span class="ui-li-text-sub">${ACTIVE}</span>
+ * <span class="ui-li-text-sub2">${FROM}</span>
+ * </li>
+ * </script>
*
- * // disable popup from javascript
- * $('#mySlider').tizenslider('option','popup',false);
+ * <ul id="virtuallist-normal_3_2_7_ul" data-role="virtuallistview" data-template="tmp-3-2-7" data-dbtable="JSON_DATA" data-row="100">
+ * </ul>
*
- * // from buttons
- * $('#popupEnabler').bind('vclick', function() {
- * $('#mySlider').tizenslider('option','popup',true);
- * });
- * $('#popupDisabler').bind('vclick', function() {
- * $('#mySlider').tizenslider('option','popup',false);
- * });
*/
/**
- @class Slider
- The slider widget shows a control on the screen that you can use to change values by dragging a handle on a horizontal scale. Sliders can be used in Tizen as described in the jQueryMobile documentation for sliders.
+ @class VirtualList
+ In the Web environment, it is challenging to display a large amount of data in a list, such as displaying a contact list of over 1000 list items. It takes time to display the entire list in HTML and the DOM manipulation is complex.
- To add a slider widget to the application, use the following code:
+ The virtual list widget is used to display a list of unlimited data elements on the screen for better performance. This widget provides easy access to databases to retrieve and display data. Virtual lists are based on the jQuery.template plugin as described in the jQuery documentation for jQuery.template plugin.
- <input data-popup='false' type="range" name="slider" value="5" min="0" max="10" data-icon="text" data-text-left="Min" data-text-right="Max" />
+ To add a virtual list widget to the application, use the following code:
- The slider can define callbacks for events as described in the jQueryMobile documentation for slider events.
- You can use methods with the slider as described in the jQueryMobile documentation for slider methods.
+ <script id="tmp-3-2-7" type="text/x-jquery-tmpl">
+ <li class="ui-li-3-2-7">
+ <span class="ui-li-text-main">${NAME}</span>
+ <img src="00_winset_icon_favorite_on.png" class="ui-li-icon-sub"/>
+ <span class="ui-li-text-sub">${ACTIVE}</span>
+ <span class="ui-li-text-sub2">${FROM}</span>
+ </li>
+ </script>
+ <ul id="vlist" data-role="virtuallistview" data-template="tmp-3-2-7" data-dbtable="JSON_DATA" data-row="100"></ul>
*/
/**
- @property {String} data-icon
- Defines the icon style for the slider ends. The icon options are bright, volume, and text.
- The default value is text.
+ @property {String} data-role
+ Creates the virtual list view. The value must be set to virtuallistview.
+ Only the >ul< element, which a id attribute defined, supports this option. Also, the vlLoadSuccess class attribute must be defined in the >ul< element to ensure that loading data from the database is complete.
*/
/**
- @property {Boolean} data-popup
- Enables or disables a pop-up showing the current value while the handle is dragged.
- The default value is true.
+ @property {String} data-template
+ Defines the jQuery.template element ID.
+ The jQuery.template must be defined. The template style can use rem units to support scalability.
*/
/**
- @property {String} data-text-left
- Defines the text displayed on the left side of the slider.
- The data-icon option must be set to text.
+ @property {Number} data-row
+ Defines the number of virtual list child elements.
+ The minimum value is 20 and the default value is 100. As the value gets higher, the loading time increases while the system performance improves. So you need to pick a value that provides the best performance without excessive loading time.
*/
/**
- @property {String} data-text-right
- Defines the text displayed on the right side of the slider.
- The data-icon option must be set to text.
+ @method create
+ @param {function} itemData(index)
+ : function itemData(index) returns the JSON object matched with the given index. The index value is between 0 and numItemData-1.
+ @param {Number} numItemData
+ : number numItemData or function numItemData() defines or returns a static number of items.
+ @param {function} cacheItemData(minIndex, maxIndex)
+ : function cacheItemData(minIndex, maxIndex) prepares the JSON data. This method is called before calling the itemData() method with index values between minIndex and maxIndex.
*/
-(function ($, window, undefined) {
- $.widget("tizen.tizenslider", $.mobile.widget, {
+(function ( $, undefined ) {
+
+ /* Code for Virtual List Demo */
+ var listCountPerPage = {}, /* Keeps track of the number of lists per page UID. This allows support for multiple nested list in the same page. https://github.com/jquery/jquery-mobile/issues/1617 */
+ _NO_SCROLL = 0, /* ENUM */
+ _SCROLL_DOWN = 1, /* ENUM */
+ _SCROLL_UP = -1; /* ENUM */
+
+ $.widget( "tizen.virtuallistview", $.mobile.widget, {
options: {
- popup: true
+ theme: "s",
+ countTheme: "s",
+ headerTheme: "s",
+ dividerTheme: "s",
+ splitIcon: "arrow-r",
+ splitTheme: "s",
+ inset: false,
+ id: "", /* Virtual list UL elemet's ID */
+ childSelector: " li", /* To support swipe list */
+ dbtable: "",
+ template : "",
+ dbkey: false, /* Data's unique Key */
+ scrollview: false,
+ row: 100,
+ page_buf: 30,
+ initSelector: ":jqmData(role='virtuallistview')"
},
- popup: null,
- handle: null,
- handleText: null,
-
- _create: function () {
- this.currentValue = null;
- this.popupVisible = false;
+ _stylerMouseUp: function () {
+ $( this ).addClass( "ui-btn-up-s" );
+ $( this ).removeClass( "ui-btn-down-s" );
+ },
- var self = this,
- inputElement = $( this.element ),
- slider,
- handle_press,
- popupEnabledAttr,
- icon,
- text_right,
- text_left,
- text_length,
- elem_left,
- elem_right,
- margin_left,
- margin_right;
+ _stylerMouseDown: function () {
+ $( this ).addClass( "ui-btn-down-s" );
+ $( this ).removeClass( "ui-btn-up-s" );
+ },
- // apply jqm slider
- inputElement.slider();
+ _stylerMouseOver: function () {
+ $( this ).toggleClass( "ui-btn-hover-s" );
+ },
- // hide the slider input element proper
- inputElement.hide();
+ _stylerMouseOut: function () {
+ $( this ).toggleClass( "ui-btn-hover-s" );
+ $( this ).addClass( "ui-btn-up-s" );
+ $( this ).removeClass( "ui-btn-down-s" );
+ },
- self.popup = $('<div class="ui-slider-popup"></div>');
+ // ?
+ // this virtuallistview object
+ // @param[in] template template name(string)
+ _pushData: function ( template ) {
+ var o = this.options,
+ i,
+ myTemplate = $( "#" + template ), // Get template object
+ // NOTE: o.row = # of rows handled at once. Default value is 100.
+ lastIndex = ( o.row > this._numItemData ? this._numItemData : o.row ), // last index of handled data
+ htmlData;
- // set the popup according to the html attribute
- popupEnabledAttr = inputElement.jqmData('popup');
- if ( popupEnabledAttr !== undefined ) {
- self.options.popup = ( popupEnabledAttr == true );
+ for ( i = 0; i < lastIndex; i++ ) {
+ htmlData = myTemplate.tmpl( this._itemData( i ) ); // Make rows with template,
+ $( o.id ).append( $( htmlData ).attr( 'id', o.itemIDPrefix + i ) ); // and append it to the vlist object
}
- // get the actual slider added by jqm
- slider = inputElement.next('.ui-slider');
-
- icon = inputElement.attr('data-icon');
-
- // wrap the background
- slider.wrap('<div class="ui-slider-container"></div>');
-
- // get the handle
- self.handle = slider.find('.ui-slider-handle');
-
- // remove the rounded corners from the slider and its children
- slider.removeClass('ui-btn-corner-all');
- slider.find('*').removeClass('ui-btn-corner-all');
-
- // add icon
- switch ( icon ) {
- case 'bright':
- case 'volume':
- elem_left = $('<div class="ui-slider-left-' + icon + '"></div>');
- elem_right = $('<div class="ui-slider-right-' + icon + '"></div>');
-
- slider.before( elem_left );
- slider.after( elem_right );
-
- margin_left = elem_left.width() + 16;
- margin_right = elem_right.width() + 16;
- break;
-
- case 'text':
- text_left = ( inputElement.attr('data-text-left') === undefined ) ? '' :
- inputElement.attr('data-text-left').substring( 0, 3 );
- text_right = ( inputElement.attr('data-text-right') === undefined ) ? '' :
- inputElement.attr('data-text-right').substring( 0, 3 );
-
- text_length = Math.max( text_left.length, text_right.length ) + 1;
-
- margin_left = text_length + "rem";
- margin_right = text_length + "rem";
-
- elem_left = $('<div class="ui-slider-left-text" style="left:' +
- -( text_length ) + 'rem; width:' + text_length + 'rem;">' +
- '<span style="position:relative;top:0.4em;">' +
- text_left +
- '</span></div>');
- elem_right = $('<div class="ui-slider-right-text" style="right:' +
- -( text_length ) + 'rem; width:' + text_length + 'rem;">' +
- '<span style="position:relative;top:0.4em;">' +
- text_right +
- '</span></div>');
+ // After pushing data re-style virtuallist widget
+ $( o.id ).trigger( "create" );
+ },
- slider.before( elem_left );
- slider.after( elem_right );
- break;
- }
+ // Set children <li> elements' position
+ //
+ // this: virtuallist element
+ // event: virtuallistview.options
+ // TODO: Why this arg name is 'event'? Not resonable.
+ // (this function is not called with event element as args!)
+ _reposition: function ( event ) {
+ var o,
+ t = this,
+ padding,
+ margin;
- if ( icon ) {
- slider.parent('.ui-slider-container').css({
- "margin-left": margin_left,
- "margin-right": margin_right
- });
+ if ( event.data ) {
+ o = event.data;
+ } else {
+ o = event;
}
+ if ( $( o.id + o.childSelector ).size() > 0 ) { // $("#vlistid li")
+ // first child's top position
+ // NOTE: the first element may not be '0'!!!
+ t._title_h = $( o.id + o.childSelector + ':first' ).position().top;
+ // first child's outer height (TODO: reuse selected items)
+ t._line_h = $( o.id + o.childSelector + ':first' ).outerHeight();
- // handle press
- slider.append($('<div class="ui-slider-handle-press"></div>'));
- self.handle_press = slider.find('.ui-slider-handle-press');
- self.handle_press.css('display', 'none');
-
- // add a popup element (hidden initially)
- slider.parents(".ui-page").append( self.popup );
- self.popup.hide();
+ // container(vlist element)'s innerwidth
+ t._container_w = $( o.id ).innerWidth();
- // get the element where value can be displayed
- self.handleText = slider.find('.ui-btn-text');
+ // get sum of container's left/right padding
+ padding = parseInt( $( o.id + o.childSelector ).css( "padding-left" ), 10 )
+ + parseInt( $( o.id + o.childSelector ).css( "padding-right" ), 10 );
- // set initial value
- self.updateSlider();
+ // Add CSS to all <li> elements
+ // * absolute position
+ // * btn-up
+ // * mouse up/down/over/out styles
+ $( o.id + ">" + o.childSelector )
+ .addClass( "position_absolute" )
+ .addClass( "ui-btn-up-s" )
+ .bind( "mouseup", t._stylerMouseUp )
+ .bind( "mousedown", t._stylerMouseDown )
+ .bind( "mouseover", t._stylerMouseOver )
+ .bind( "mouseout", t._stylerMouseOut );
+ }
- // bind to changes in the slider's value to update handle text
- this.element.bind('change', function () {
- self.updateSlider();
- });
+ // Set absolute top/left position of each <li>
+ $( o.id + ">" + o.childSelector ).each( function ( index ) {
+ margin = parseInt( $( this ).css( "margin-left" ), 10 )
+ + parseInt( $( this ).css( "margin-right" ), 10 );
- // bind clicks on the handle to show the popup
- self.handle.bind('vmousedown', function () {
- self.showPopup();
- });
+ $( this ).css( "top", t._title_h + t._line_h * index + 'px' )
+ .css( "width", t._container_w - padding - margin );
+ } );
- // watch events on the document to turn off the slider popup
- slider.add( document ).bind('vmouseup', function () {
- self.hidePopup();
- });
+ // Set Max Listview Height
+ $( o.id ).height( t._numItemData * t._line_h );
},
- _handle_press_show: function () {
- this.handle_press.css('display', '');
- },
+ // Resize each listitem's width
+ _resize: function ( event ) {
+ var o, // 'ul'
+ t = this,
+ li,
+ padding,
+ margin;
- _handle_press_hide: function () {
- this.handle_press.css('display', 'none');
- },
+ if ( event.data ) {
+ o = event.data;
+ } else {
+ o = event;
+ }
+ li = $( o ).children( o.childSelector )
- // position the popup
- positionPopup: function () {
- var dstOffset = this.handle.offset();
+ t._container_w = $( o ).width();
- this.popup.offset({
- left: dstOffset.left + ( this.handle.width() - this.popup.width() ) / 2,
- top: dstOffset.top - this.popup.height()
- });
+ padding = parseInt( li.css( "padding-left" ), 10 )
+ + parseInt( li.css( "padding-right" ), 10 );
- this.handle_press.offset({
- left: dstOffset.left,
- top: dstOffset.top
- });
+ li.each( function ( index, obj ) {
+ margin = parseInt( $( this ).css( "margin-left" ), 10 )
+ + parseInt( $( this ).css( "margin-right" ), 10 );
+ $( this ).css( "width", t._container_w - padding - margin );
+ } );
},
- // show value on the handle and in popup
- updateSlider: function () {
- var font_size,
- font_length,
- font_top,
- padding_size,
- newValue,
- get_value_length = function ( v ) {
- var val = Math.abs( v ),
- len;
+ // New scrollmove function supporting scrollTo
+ _scrollmove: function ( ev ) {
+ var t = ev.data, // vlist (JQM object)
+ o = t.options, // options
+ prevTopBufLen = t._num_top_items, // Previous(remembered) top buf length
+ timerInterval = 100,
+ i,
+ _scrollView,
+ _normalScroll;
- if ( val > 999 ) {
- len = 4;
- } else if ( val > 99 ) {
- len = 3;
- } else if ( val > 9 ) {
- len = 2;
- } else {
- len = 1;
+ _scrollView = {
+ viewTop: function ( ) {
+ var sv = $( o.id ).parentsUntil( ".ui-page" ).find( ".ui-scrollview-view" ),
+ svTrans = sv.css( "-webkit-transform" ),
+ svTransVal = "0,0,0,0,0,0";
+ if ( svTrans ) {
+ svTransVal = svTrans.replace( /matrix\s*\((.*)\)/, "$1" ); // matrix(a,c,b,d,tx,ty)
}
+ return - parseInt( svTransVal.split(',')[5], 10 );
+ }
+ };
+ _normalScroll = {
+ viewTop: function ( ) {
+ return $( window ).scrollTop( ); // TODO: - _line_h?
+ }
+ };
+ // Get current view top position
+ function viewTop ( ) {
+ return o.scrollview ? _scrollView.viewTop() : _normalScroll.viewTop();
+ }
+ // log function for debug
+ function log ( msg ) {
+ var debug = false;
+ if ( debug ) {
+ console.log( ">>virtualllist: " + msg );
+ }
+ }
- if ( v < 0 ) {
- len++;
- }
+ // Timer interval function
+ // @param[in] vl virtuallist object (JQM object)
+ function timerMove ( vl, undefined ) {
+ var cy, // current y position
+ cti, // current top idx
+ cbi, // current bottom idx
+ oti = vl._first_index, // old top idx
+ obi = vl._last_index, // old botton idx
+ dti, // delta of top idx
+ fromIdx,
+ toIdx, // index range to be moved
+ delta, // moveItem delta
+ rowLen = vl.options.row, // max. # of items handled at once
+ bufSize, // top/bottom buffer size. unit: # of items
+ i;
- return len;
- };
+ // subroutine: Move itemContents in i2 into i1
+ function moveItemContents( vl, i1, i2 ) {
+ // TODO: Find a efficient way to replace data!
+ // Assumption: i1 and i2 has same children.
+ var NODETYPE = { ELEMENT_NODE: 1, TEXT_NODE: 3 },
+ c1, // child item 1 (old)
+ c2, // child item 2 (new)
+ newText,
+ newImg,
+ i;
- // remove the title attribute from the handle (which is
- // responsible for the annoying tooltip); NB we have
- // to do it here as the jqm slider sets it every time
- // the slider's value changes :(
- this.handle.removeAttr('title');
+ $( i1 ).find( ".ui-li-text-main", ".ui-li-text-sub", ".ui-li-text-sub2", "ui-btn-text" ).each( function ( index ) {
+ c1 = $( this );
+ newText = $( i2 ).find( ".ui-li-text-main", ".ui-li-text-sub", "ui-btn-text" ).eq( index ).text();
- newValue = this.element.val();
+ $( c1 ).contents().filter( function () {
+ return ( this.nodeType == NODETYPE.TEXT_NODE );
+ } ).get( 0 ).data = newText;
+ } );
- font_length = get_value_length( newValue );
+ $( i1 ).find( "img" ).each( function ( imgIdx ) {
+ var c1 = $( this );
+ newImg = $( i2 ).find( "img" ).eq( imgIdx ).attr( "src" );
- if ( this.popupVisible ) {
- this.positionPopup();
+ $( c1 ).attr( "src", newImg );
+ } );
- switch ( font_length ) {
- case 1:
- case 2:
- font_size = '1.5rem';
- padding_size = '0.15rem';
- break;
- case 3:
- font_size = '1rem';
- padding_size = '0.5rem';
- break;
- default:
- font_size = '0.8rem';
- padding_size = '0.5rem';
- break;
+ $( i1 ).removeData( ); // Clear old data
}
- this.popup.css({
- "font-size": font_size,
- "padding-top": padding_size
- });
- }
-
- if ( newValue === this.currentValue ) {
- return;
- }
-
- switch ( font_length ) {
- case 1:
- font_size = '0.95rem';
- font_top = '0';
- break;
- case 2:
- font_size = '0.85rem';
- font_top = '-0.01rem';
- break;
- case 3:
- font_size = '0.65rem';
- font_top = '-0.05rem';
- break;
- default:
- font_size = '0.45rem';
- font_top = '-0.15rem';
- break;
- }
-
- if ( font_size != this.handleText.css('font-size') ) {
- this.handleText.css({
- 'font-size': font_size,
- 'top': font_top
- });
- }
-
- this.currentValue = newValue;
- this.handleText.text( newValue );
- this.popup.html( newValue );
+ // subroutine: Move item
+ function moveItem( vl, fromIdx, toIdx ) {
+ var itemData, // data from itemData()
+ item, // item element
+ newItem, // new item element
+ tmpl; // template
- this.element.trigger( 'update', newValue );
- },
+ log( ">> move item: " + fromIdx + " --> " + toIdx );
- // show the popup
- showPopup: function () {
- if ( !this.options.popup || this.popupVisible ) {
- return;
- }
+ // Find current item
+ item = $( '#' + vl.options.itemIDPrefix + fromIdx ); // TODO: refactor ID generation!
+ if ( ! item || ! item.length ) {
+ return false;
+ }
- this.popup.show();
- this.popupVisible = true;
- this._handle_press_show();
- },
+ // Get new item
+ tmpl = $( "#" + vl.options.template );
+ if ( tmpl ) {
+ newItem = tmpl.tmpl( vl._itemData( toIdx ) );
- // hide the popup
- hidePopup: function () {
- if ( !this.options.popup || !this.popupVisible ) {
- return;
- }
+ // TODO: Consider touch block while moving?
- this.popup.hide();
- this.popupVisible = false;
- this._handle_press_hide();
- },
+ // Move item contents
+ moveItemContents( vl, item, newItem );
- _setOption: function (key, value) {
- var needToChange = ( value !== this.options[key] );
+ // clean up temporary item
+ newItem.remove();
+ }
- if ( !needToChange ) {
- return;
- }
+ // Move position, and set id
+ item.css( 'top', toIdx * vl._line_h )
+ .attr( 'id' , vl.options.itemIDPrefix + toIdx ); // TODO: refactor ID generation!
- switch ( key ) {
- case 'popup':
- this.options.popup = value;
+ // TODO: Apply jqmdata? check following old code;
+ // $( oldItem ).removeData( ); // Clear old data
+ // if (key) { $( oldItem ).data( key, $( newItem ).data( key ) ); }
- if ( this.options.popup) {
- this.updateSlider();
- } else {
- this.hidePopup();
+ return true;
}
- break;
- }
- }
- });
- // stop jqm from initialising sliders
- $( document ).bind( "pagebeforecreate", function ( e ) {
- if ( $.data( window, "jqmSliderInitSelector" ) === undefined ) {
- $.data( window, "jqmSliderInitSelector",
- $.mobile.slider.prototype.options.initSelector );
- $.mobile.slider.prototype.options.initSelector = null;
- }
- });
+ // Get current view position
+ cy = viewTop();
- // initialise sliders with our own slider
- $( document ).bind( "pagecreate create", function ( e ) {
- var jqmSliderInitSelector = $.data( window, "jqmSliderInitSelector" );
- $( e.target ).find(jqmSliderInitSelector).each(function () {
- var $this = $( this );
- if ( $this.is("select") ) {
- $this.slider();
- } else {
- $this.tizenslider();
- }
- });
- });
+ // Calculate bufSize: rowLen / 3
+ // NOTE: Assumption: total row length = visible items * 3 (upper+visible+lower)
+ bufSize = Math.ceil( rowLen / 3 );
-}( jQuery, this ));
+ // Calculate current top/bottom index (to be applied)
+ // top index = current position / line height
+ cti = Math.floor( cy / vl._line_h ) - bufSize; // TODO: consider buffer!
+ cbi = cti + rowLen - 1;
+ if ( cti < 0 ) { // Top boundary check
+ cbi += ( - cti );
+ cti = 0;
+ } else if ( cbi > ( vl._numItemData - 1 ) ) { // Bottom boundary check
+ cti -= ( cbi - ( vl._numItemData - 1 ) );
+ cbi = ( vl._numItemData - 1 );
+ }
+ // Calculate dti
+ dti = cti - oti;
+ log( "cy=" + cy + ", oti=" + oti + ", obi=" + obi + ", cti=" + cti + ", cbi=" + cbi + ", dti=" + dti );
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Authors: Wonseop Kim ( wonseop.kim@samsung.com )
-*/
+ // switch: dti = 0 --> timer stop condition: delta=0 or scrollstop event comes. END.
+ if ( 0 == dti ) {
+ // Check timer runtime
+ vl.timerStillCount += 1;
+ if ( vl.timerStillCount < 12 ) { // check count ( TODO: test and adjust )
+ log("dti=0 " + vl.timerStillCount + " times");
+ vl.timerMoveID = setTimeout( timerMove, timerInterval, vl ); // run once more
+ return;
+ }
-/**
- * "Handler" is a widget helping a user to scroll a window or panel.
- * It is different from the scrollview feature in that the handler has a fixed size
- * and disappears when a scroll size is smaller than a parent window's size.
- * If the handler widget is activated, a scroll bar on the screen will be deactivated.
- * The handler widget supports scrolling up and down and indicates the position of the scrolled window.
- *
- * HTML Attributes:
- *
- * data-handler : This attribute is indicating that whether enable.
- * If you want to use, you will set 'true'.
- * data-handler-theme : Set the widget theme ( optional )
- *
- * APIs:
- *
- * enableHandler ( boolean )
- * : Get or set the use of handler widget.
- * If the value is "true", it will be run handler widget.
- * If the value is "false", it will be not run handler widget.
- * If no value is specified, will act as a getter.
- *
- * Events:
- *
- * Examples:
- *
- * <div data-role="content" data-scroll="y" data-handler="true">
- * <ul data-role="listview">
- * <li data-role="list-divider">A</li>
- * <li><a href="#">Adam Kinkaid</a></li>
- * ...
- * </ul>
- * </div>
- */
+ log("dti=0 " + vl.timerStillCount + " times. End timer.");
+ vl.timerStillCount = 0;
+ // Stop timer
+ if ( vl.timerMoveID ) {
+ clearTimeout( vl.timerMoveID );
+ vl.timerMoveID = null;
+ }
+ } else {
+ // switch: dti >= # of max elements --> total replace.
+ vl.timerStillCount = 0; // Reset still counter
-/**
- @class handler
- The handler widget enables the user to vertically scroll through a page or panel using a fixed-size handle. The widget indicates the position of the scrolled window, and only appears on the screen if the parent page or panel's scroll size is larger than the screen size. <br/> To add a handler widget to the application, use the following code:
+ if ( Math.abs( dti ) >= rowLen ) {
+ fromIdx = oti;
+ toIdx = obi;
+ delta = dti;
+ log( ">>> WHOLE CHANGE! delta=" + delta );
+ } else {
+ // switch: dti < # of max elements --> move t2b or b2t until new top/bottom idx is covered
+ if ( dti > 0 ) {
+ fromIdx = oti;
+ toIdx = oti + dti - 1;
+ delta = rowLen;
+ } else {
+ fromIdx = obi + dti + 1; // dti < 0
+ toIdx = obi;
+ delta = -rowLen;
+ }
+ log( ">>> partial change. delta=" + delta );
+ }
- <div data-role="content" data-scroll="y" data-handler="true">
- <ul data-role="listview">
- <li data-role="list-divider">A</li>
- <li><a href="#">Adam Kinkaid</a></li>
- ...
- </ul>
- </div>
-
- You can use the enableHandler method with the handler widget to get (if no value is defined) or set the handler usage status. If the [enable] value is true, the handler is enabled; otherwise the handler is not used.
+ // Move items
+ for ( i = fromIdx; i <= toIdx; i++ ) {
+ moveItem( vl, i, i + delta ); // Change data and position
+ }
- $("#.selector").scrollview("enableHandler", [enable]);
-*/
-/**
- @property {Boolean} data-handler
- Enables the handler widget. The value must be set to true.
-*/
-/**
- @property {String} data-handler-theme
- Sets the handler widget theme.
-*/
-( function ( $, document, undefined ) {
- // The options of handler in scrollview
- $.tizen.scrollview.prototype.options.handler = false;
- $.tizen.scrollview.prototype.options.handlerTheme = "s";
+ // Store current top/bottom idx into vl
+ vl._first_index = cti;
+ vl._last_index = cbi;
- var originSetOption = $.tizen.scrollview.prototype._setOption,
- createHandler = function ( target ) {
- var $view = target,
- prefix = "<div class=\"ui-handler ui-handler-direction-",
- suffix = "\"><div class=\"ui-handler-track\"><div class=\"ui-handler-thumb\"></div></div></div>",
- scrollview = $view.data( "scrollview" ),
- options = scrollview.options,
- direction = options.direction,
- parentTheme = $.mobile.getInheritedTheme( scrollview, "s" ),
- theme = options.theme || parentTheme,
- isHorizontal = ( scrollview.options.direction === "x" ),
- _$view = scrollview._$view,
- _$clip = scrollview._$clip,
- scrollbar = $view.find( ".ui-scrollbar" ),
- handler = null,
- handlerThumb = null,
- viewLength = 0,
- clipLength = 0,
- handlerHeight = 0,
- handlerMargin = 0,
- trackLength = 0,
- moveTimer,
- isTouchable = $.support.touch,
- dragStartEvt = ( isTouchable ? "touchstart" : "mousedown" ) + ".handler",
- dragMoveEvt = ( isTouchable ? "touchmove" : "mousemove" ) + ".handler",
- dragStopEvt = ( isTouchable ? "touchend" : "mouseup" ) + ".handler",
- dragLeaveEvt = ( isTouchable ? " touchleave" : " mouseleave" ) + ".handler",
- calculateLength = function () {
- clipLength = ( isHorizontal ? _$clip.width() : _$clip.height() );
- viewLength = ( isHorizontal ? _$view.width() : _$view.height() ) - clipLength;
- trackLength = clipLength - handlerHeight - handlerMargin * 2;
- },
- setHanderPostion = function ( scrollPos ) {
- var handlerPos = Math.round( ( isHorizontal ? scrollPos.x : scrollPos.y ) / viewLength * trackLength );
- handlerThumb[0].style[ ( isHorizontal ? "left" : "top" ) ] = handlerPos + "px";
- },
- stopHandlerScroll = function () {
- $( document ).unbind( ".handler" );
- $view.moveData = null;
- _$view.trigger( "scrollstop" );
- };
+ // Register timer to check again
+ vl.timerMoveID = setTimeout( timerMove, timerInterval, vl );
+ }
+ return; // End of function
+ }
+
+ // ==== function start ====
+
+ t.timerStillCount = 0; // Count do-nothing time. For behavior tuning.
- if ( $view.find( ".ui-handler-thumb" ).length !== 0 || typeof direction !== "string" ) {
- return;
+ // If a timer function is alive, clear it
+ if ( t.timerMoveID ) {
+ clearTimeout( t.timerMoveID );
+ t.timerMoveID = null;
}
+ // run TimerMove()
+ timerMove( t );
+ },
- handler = $( [ prefix, direction, suffix ].join( "" ) ).appendTo( $view.addClass( " ui-handler-" + theme ) );
- handlerThumb = $view.find( ".ui-handler-thumb" ).attr( {
- "tabindex" : "0",
- "aria-label" : ( isHorizontal ? "Horizontal handler, double tap and move to scroll" : "Verticalhandler, double tap and move to scroll" )
- }).hide();
- handlerHeight = ( isHorizontal ? handlerThumb.width() : handlerThumb.height() );
- handlerMargin = ( isHorizontal ? parseInt( handler.css( "right" ), 10 ) : parseInt( handler.css( "bottom" ), 10 ) );
+ _recreate: function ( newArray ) {
+ var t = this,
+ o = this.options;
- $.extend( $view, {
- moveData : null
- });
+ $( o.id ).empty();
- // handler drag
- handlerThumb.bind( dragStartEvt, {
- e : handlerThumb[0]
- }, function ( event ) {
- scrollview._stopMScroll();
+ t._numItemData = newArray.length;
+ t._direction = _NO_SCROLL;
+ t._first_index = 0;
+ t._last_index = o.row - 1;
- var target = event.data.e,
- t = ( isTouchable ? event.originalEvent.targetTouches[0] : event );
+ t._pushData( o.template );
- target.style.opacity = 1.0;
+ if (o.childSelector == " ul" ) {
+ $( o.id + " ul" ).swipelist();
+ }
- $view.moveData = {
- target : target,
- X : parseInt( target.style.left, 10 ) || 0,
- Y : parseInt( target.style.top, 10 ) || 0,
- pX : t.pageX,
- pY : t.pageY
- };
- calculateLength();
+ $( o.id ).virtuallistview();
- _$view.trigger( "scrollstart" );
+ t.refresh( true );
- if ( !isTouchable ) {
- event.preventDefault();
- }
+ t._reposition( o );
+ },
- $( document ).bind( dragMoveEvt, function ( event ) {
- var moveData = $view.moveData,
- target = moveData.target,
- handlePos = 0,
- scrollPos = 0,
- t = ( isTouchable ? event.originalEvent.targetTouches[0] : event );
+ // Init virtuallistview
+ // this virtuallistview object
+ _initList: function () {
+ var t = this,
+ o = this.options;
- handlePos = ( isHorizontal ? moveData.X + t.pageX - moveData.pX : moveData.Y + t.pageY - moveData.pY );
+ /* After AJAX loading success */
- if ( handlePos < 0 ) {
- handlePos = 0;
- }
+ // Put initial <li> elements
+ t._pushData( o.template );
- if ( handlePos > trackLength ) {
- handlePos = trackLength;
- }
- scrollPos = - Math.round( handlePos / trackLength * viewLength );
+ // find a parent page, and run _reposition() at 'pageshow' event
+ // TODO: Consider replace parentsUntil().parent() to parent('.ui-page') ???
+ $( o.id ).parentsUntil( ".ui-page" ).parent().one( "pageshow", function () {
+ setTimeout( function () {
+ t._reposition( o );
+ }, 0);
+ });
- if ( isHorizontal ) {
- scrollview._setScrollPosition( scrollPos, 0 );
- target.style.left = handlePos + "px";
- } else {
- scrollview._setScrollPosition( 0, scrollPos );
- target.style.top = handlePos + "px";
- }
+ // Bind _scrollmove() at 'scrollstart.virtuallist' event
+ $( document ).bind( "scrollstart.virtuallist scrollstop.vrituallist", t, t._scrollmove );
- event.preventDefault();
- }).bind( dragStopEvt + dragLeaveEvt, function ( event ) {
- stopHandlerScroll();
- });
- });
+ // Bind _resize()
+ $( window ).on( "throttledresize", $( o.id ), t._resize );
- _$view.bind( dragStopEvt, function ( event ) {
- stopHandlerScroll();
+ // when ul is a childselector, assume that this is also a swipelist,
+ // and run swipelist constructor
+ if ( o.childSelector == " ul" ) {
+ $( o.id + " ul" ).swipelist();
+ }
+
+ t.refresh( true );
+ },
+
+ create: function () {
+ var o = this.options;
+
+ /* external API for AJAX callback */
+ this._create.apply( this, arguments );
+
+ // TODO: remove this line? _initList() calls reposition...
+ this._reposition( o );
+ },
+
+ _create: function ( args ) {
+ // Extend instance variables
+ $.extend( this, {
+ _itemData : function ( idx ) { return null; },
+ _numItemData : 0,
+ _cacheItemData : function ( minIdx, maxIdx ) { },
+ _title_h : 0,
+ _container_w : 0,
+ _minimum_row : 100,
+ _direction : _NO_SCROLL,
+ _first_index : 0,
+ _last_index : 0,
+ _num_top_items : 0 // By scroll move, number of hidden elements.
+ } );
+
+ // local variables
+ var t = this,
+ o = this.options,
+ $el = this.element,
+ shortcutsContainer = $('<div class="ui-virtuallist"/>'),
+ shortcutsList = $('<ul></ul>'),
+ dividers = $el.find(':jqmData(role="virtuallistview" )'),
+ lastListItem = null,
+ shortcutscroll = this,
+ dbtable_name,
+ dbtable;
+
+
+ // Add CSS classes to $el (=virtuallistview)
+ $el.addClass( function ( i, orig ) {
+ return orig + " ui-listview ui-virtual-list-container" + ( t.options.inset ? " ui-listview-inset ui-corner-all ui-shadow " : "" );
});
- $view.bind( "scrollstart", function ( event ) {
- if ( !scrollview.enableHandler() ) {
- return;
- }
+ // keep the vlist's ID
+ o.itemIDPrefix = $el.attr( "id" ) + '_';
+ o.id = "#" + $el.attr( "id" );
- calculateLength();
+ // when page hides, empty all child elements
+ $( o.id ).bind( "pagehide", function ( e ) {
+ $( o.id ).empty();
+ });
- if ( viewLength < 0 || clipLength < handlerHeight ) {
- if ( scrollbar.is( ":hidden" ) ) {
- scrollbar.show();
- }
- return;
- }
+ // Find if scrollview is used
+ if ( $( ".ui-scrollview-clip" ).size() > 0 ) {
+ o.scrollview = true;
+ } else {
+ o.scrollview = false;
+ }
- if ( scrollbar.is( ":visible" ) ) {
- scrollbar.hide();
- }
+ // Calculate page buffer size
+ if ( $el.data( "row" ) ) {
+ o.row = $el.data( "row" );
- if ( moveTimer ) {
- clearInterval( moveTimer );
- moveTimer = undefined;
+ if ( o.row < t._minimum_row ) {
+ o.row = t._minimum_row;
}
- handler.addClass( "ui-handler-visible" );
- handlerThumb.stop( true, true )
- .fadeIn();
- }).bind( "scrollupdate", function ( event, data ) {
- if ( !scrollview.enableHandler() || viewLength < 0 || clipLength < handlerHeight ) {
+ o.page_buf = parseInt( ( o.row / 2 ), 10 );
+ }
+
+ // Get arguments
+ if ( args ) {
+ if ( args.itemData && typeof args.itemData == 'function' ) {
+ t._itemData = args.itemData;
+ } else {
return;
}
-
- setHanderPostion( scrollview.getScrollPosition() );
- }).bind( "scrollstop", function ( event ) {
- if ( !scrollview.enableHandler() || viewLength < 0 || clipLength < handlerHeight ) {
+ if ( args.numItemData ) {
+ if ( typeof args.numItemData == 'function' ) {
+ t._numItemData = args.numItemData( );
+ } else if ( typeof args.numItemData == 'number' ) {
+ t._numItemData = args.numItemData;
+ } else {
+ return;
+ }
+ } else {
return;
}
+ } else { // No option is given
+ // Legacy support: dbtable
+ console.warn( "WARNING: The data interface of virtuallist is changed. \nOld data interface(data-dbtable) is still supported, but will be removed in next version. \nPlease fix your code soon!" );
- moveTimer = setInterval( function () {
- setHanderPostion( scrollview.getScrollPosition() );
- if ( !scrollview._gesture_timer ) {
- clearInterval( moveTimer );
- moveTimer = undefined;
+ /* After DB Load complete, Init Vritual list */
+ if ( $( o.id ).hasClass( "vlLoadSuccess" ) ) {
+ dbtable_name = $el.jqmData('dbtable');
+ dbtable = window[ dbtable_name ];
+
+ $( o.id ).empty();
+
+ if ( !dbtable ) {
+ dbtable = { };
}
- }, 10 );
- if ( scrollview._handlerTimer ) {
- clearTimeout( scrollview._handlerTimer );
- scrollview._handlerTimer = 0;
+ t._itemData = function ( idx ) {
+ return dbtable[ idx ];
+ };
+ t._numItemData = dbtable.length;
+ } else {
+ return; // Do nothing
}
- scrollview._handlerTimer = setTimeout( function () {
- if ( scrollview._timerID === 0 && $view.moveData === null ) {
- handlerThumb.stop( true, true )
- .css( "opacity", 1.0 )
- .fadeOut( function () {
- handler.removeClass( "ui-handler-visible" );
- });
- scrollview._handlerTimer = 0;
- }
- }, 1000 );
- }).bind( "mousewheel", function ( event ) {
- handler.removeClass( "ui-handler-visible" );
- setHanderPostion( scrollview.getScrollPosition() );
- });
- };
+ }
+
+ // Get template data
+ if ( $el.data( "template" ) ) {
+ o.template = $el.data( "template" );
+
+ /* to support swipe list, <li> or <ul> can be main node of virtual list. */
+ if ( $el.data( "swipelist" ) == true ) {
+ o.childSelector = " ul";
+ } else {
+ o.childSelector = " li";
+ }
+ }
- $.extend( $.tizen.scrollview.prototype, {
- enableHandler: function ( enabled ) {
- if ( typeof enabled === 'undefined' ) {
- return this.options.handler;
+ // Set data's unique key
+ // NOTE: Unnecessary?
+ if ( $el.data( "dbkey" ) ) {
+ o.dbkey = $el.data( "dbkey" );
}
- this.options.handler = !!enabled;
+ t._first_index = 0; // initial top idx of <li> element.
+ t._last_index = o.row - 1; // initial bottom idx of <li> element.
+ t._initList(); // NOTE: Called at here only!
+ },
- var $view = this.element;
- if ( this.options.handler ) {
- if ( $view.find( ".ui-handler" ).length === 0 ) {
- createHandler( $view );
- }
+ destroy : function () {
+ var o = this.options;
- $view.find( ".ui-scrollbar" ).hide();
- $view.find( ".ui-handler" ).show();
- } else {
- $view.find( ".ui-handler" ).removeClass( "ui-handler-visible" ).hide();
- $view.find( ".ui-scrollbar" ).show();
+ $( document ).unbind( "scrollstop" );
+
+ $( window ).off( "throttledresize", this._resize );
+
+ $( o.id ).empty();
+
+ if ( this.timerMoveID ) {
+ clearTimeout( this.timerMoveID );
+ this.timerMoveID = null;
}
},
- _setHandlerTheme: function ( handlerTheme ) {
- if ( !handlerTheme ) {
- return;
+ _itemApply: function ( $list, item ) {
+ var $countli = item.find( ".ui-li-count" );
+
+ if ( $countli.length ) {
+ item.addClass( "ui-li-has-count" );
}
- var oldClass = "ui-handler-" + this.options.handlerTheme,
- newClass = "ui-handler-" + handlerTheme;
+ $countli.addClass( "ui-btn-up-" + ( $list.jqmData( "counttheme" ) || this.options.countTheme ) + " ui-btn-corner-all" );
- this.element.removeClass( oldClass ).addClass( newClass );
- this.options.handlerTheme = handlerTheme;
+ // TODO class has to be defined in markup
+ item.find( "h1, h2, h3, h4, h5, h6" ).addClass( "ui-li-heading" ).end()
+ .find( "p, dl" ).addClass( "ui-li-desc" ).end()
+ .find( ">img:eq(0), .ui-link-inherit>img:eq(0)" ).addClass( "ui-li-thumb" ).each( function () {
+ item.addClass( $( this ).is( ".ui-li-icon" ) ? "ui-li-has-icon" : "ui-li-has-thumb" );
+ }).end()
+ .find( ".ui-li-aside" ).each(function () {
+ var $this = $( this );
+ $this.prependTo( $this.parent() ); //shift aside to front for css float
+ } );
},
- _setOption: function ( key, value ) {
- switch ( key ) {
- case "handler":
- this.enableHandler( value );
- break;
- case "handlerTheme":
- this._setHandlerTheme( value );
- break;
- default:
- originSetOption.call( this, key, value );
+ _removeCorners: function ( li, which ) {
+ var top = "ui-corner-top ui-corner-tr ui-corner-tl",
+ bot = "ui-corner-bottom ui-corner-br ui-corner-bl";
+
+ li = li.add( li.find( ".ui-btn-inner, .ui-li-link-alt, .ui-li-thumb" ) );
+
+ if ( which === "top" ) {
+ li.removeClass( top );
+ } else if ( which === "bottom" ) {
+ li.removeClass( bot );
+ } else {
+ li.removeClass( top + " " + bot );
}
},
- _handlerTimer : 0
- });
+ _refreshCorners: function ( create ) {
+ var $li,
+ $visibleli,
+ $topli,
+ $bottomli;
- $( document ).delegate( ":jqmData(scroll)", "scrollviewcreate", function () {
- var widget = $( this );
- if ( widget.attr( "data-" + $.mobile.ns + "scroll" ) === "none"
- || widget.attr( "data-" + $.mobile.ns + "handler" ) !== "true" ) {
- return;
- }
- widget.scrollview( "enableHandler", "true" );
- });
-} ( jQuery, document ) );
+ if ( this.options.inset ) {
+ $li = this.element.children( "li" );
+ // at create time the li are not visible yet so we need to rely on .ui-screen-hidden
+ $visibleli = create ? $li.not( ".ui-screen-hidden" ) : $li.filter( ":visible" );
+ this._removeCorners( $li );
+ // Select the first visible li element
+ $topli = $visibleli.first()
+ .addClass( "ui-corner-top" );
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Author: Kangsik Kim <kangsik81.kim@samsung.com>
- * Minkyeong Kim <minkyeong.kim@samsung.com>
-*/
+ $topli.add( $topli.find( ".ui-btn-inner" ) )
+ .find( ".ui-li-link-alt" )
+ .addClass( "ui-corner-tr" )
+ .end()
+ .find( ".ui-li-thumb" )
+ .not( ".ui-li-icon" )
+ .addClass( "ui-corner-tl" );
-/**
- * The TokenTextArea widget changes a text item to a button. It can be comprised of a number of button widgets.
- * When a user types text and the text gets a specific event to change from a text to a button,
- * the input text is changed to a TokenTextArea widget.
- * A user can add the TokenTextArea widget to a contact list, email list, or another list.
- * The typical use of this widget is composing a number of contacts or phone numbers in a specific area of the screen.
- *
- * HTML Attributes:
- *
- * data-link : Represents the id of the page or the URL of other HTML file.
- * The page contains data for the user, for example, an address book.
- * If the value is null, anchor button doesn't work. (Default : null)
- * data-label: Provide a label for a user-guide. (Default : 'To : ')
- * data-description : This attribute is managing message format.
- * This message is displayed when widget status was changed to 'focusout'. (Default : '+ {0}')
- *
- * APIs:
- *
- * inputtext ( [string] )
- * : If argument is not exist, will get a string from inputbox.
- * If argument is exist, will set a string to inputbox.
- * select ( [number] )
- * : If no argument exists, gets a string of the selected block.
- * If any button isn't selected on a token text area widget, this method returns "null" value.
- * When a user call this method with an argument which is a number type,
- * this method selects the button which is matched with the argument.
- * add ( text, [number] )
- * : If second argument does not exist, will insert to a new button at last position.
- * Insert a new button at indexed position. The position is decided by the second argument.
- * "index of position" means that the position of inserting a new button is decided by the second argument on "add" method.
- * For example, if a user call the method like this "add("Tizen", 2)",
- * new button labed "Tizen" will be inserted on the third position.
- * remove ( [number] )
- * : If no argument exists, all buttons are removed.
- * Remove a button at indexed position.
- * The position is decided by the second argument. (index: index of button)
- * length ( void )
- * : Get a number of buttons.
- * foucsIn ( void )
- * : This method change a status to 'focusin'.
- * This status is able to manage a widget.
- * focusOut ( void )
- * : Changes the focus status to 'focus out'.
- * The status is not able to manage a widget.
- * All buttons that contained in the widget are removed and
- * summarized message is displayed.
- * destroy ( void )
- * : Remove all of the new DOM elements for the current widget that you created.
- *
- * Events:
- *
- * select : Occur when a button is selected.
- * add : Occur when new button is inserted. (@since Tizen 2.1 deprecated, You can still use this event. But not recommended.)
- * remove : Occur when a button is removed. (@since Tizen 2.1 deprecated, You can still use this event. But not recommended.)
- *
- * Examples:
- *
- * <div data-role="tokentextarea" data-label="To : " data-link="#pageId" data-description="+ {0}">
- * </div>
- *
- */
+ // Select the last visible li element
+ $bottomli = $visibleli.last()
+ .addClass( "ui-corner-bottom" );
+ $bottomli.add( $bottomli.find( ".ui-btn-inner" ) )
+ .find( ".ui-li-link-alt" )
+ .addClass( "ui-corner-br" )
+ .end()
+ .find( ".ui-li-thumb" )
+ .not( ".ui-li-icon" )
+ .addClass( "ui-corner-bl" );
+ }
+ },
-/**
- @class TokenTextArea
- The TokenTextArea widget enables the user to enter text and convert it to a button. Each button that is created from entered text as a result of a change event forms a token text area widget. This widget is useful in composing an e-mail or SMS message to a group of addresses, each of which is a clickable item for more actions, such as copying, editing, or removing the address.
+ // this virtuallistview object
+ refresh: function ( create ) {
+ this.parentPage = this.element.closest( ".ui-page" );
+ // Make sub page, and move the virtuallist into it...
+ // NOTE: check this subroutine.
+ this._createSubPages();
- To add a token text area widget to the application, use the following code:
+ var o = this.options,
+ $list = this.element,
+ self = this,
+ dividertheme = $list.jqmData( "dividertheme" ) || o.dividerTheme,
+ listsplittheme = $list.jqmData( "splittheme" ),
+ listspliticon = $list.jqmData( "spliticon" ),
+ li = $list.children( "li" ),
+ counter = $.support.cssPseudoElement || !$.nodeName( $list[ 0 ], "ol" ) ? 0 : 1,
+ item,
+ itemClass,
+ temTheme,
+ a,
+ last,
+ splittheme,
+ countParent,
+ icon,
+ pos,
+ numli,
+ itemTheme;
- <div data-role="tokentextarea" data-label="To : " data-link="#pageId">
- </div>
-*/
+ // TODO: ?
+ if ( counter ) {
+ $list.find( ".ui-li-dec" ).remove();
+ }
+
+ for ( pos = 0, numli = li.length; pos < numli; pos++ ) {
+ item = li.eq( pos );
+ itemClass = "ui-li";
+
+ // If we're creating the element, we update it regardless
+ if ( create || !item.hasClass( "ui-li" ) ) {
+ itemTheme = item.jqmData( "theme" ) || o.theme;
+ a = item.children( "a" );
-/**
- @property {String} data-label
- Sets a label as a guide for the user.
- For example, while composing an e-mail message, the 'To : ' label is a guide for the user to enter e-mail addresses.
+ if ( a.length ) {
+ icon = item.jqmData( "icon" );
- <div data-role="tokentextarea" data-label="To : ">
- </div>
-*/
+ item.buttonMarkup({
+ wrapperEls: "div",
+ shadow: false,
+ corners: false,
+ iconpos: "right",
+ /* icon: a.length > 1 || icon === false ? false : icon || "arrow-r",*/
+ icon: false, /* Remove unnecessary arrow icon */
+ theme: itemTheme
+ });
-/**
- @property {String} data-decription
- Manages the message format.
- The message is displayed when the widget status changes to focus out
+ if ( ( icon != false ) && ( a.length == 1 ) ) {
+ item.addClass( "ui-li-has-arrow" );
+ }
- <div data-role="tokentextarea" data-description=" + {0}">
- </div>
- */
-/**
- @property {String} data-link
- Sets the ID of the page or the URL of other HTML file to which the button links.
- If the data-link is set with the URL of other HTML file, the 'dom-cache' option of both page - a page containing a Tokentextarea and a page in the target HTML file - must be set as 'true'.
+ a.first().addClass( "ui-link-inherit" );
- <div data-role="tokentextarea" data-link="#pageId">
- </div>
+ if ( a.length > 1 ) {
+ itemClass += " ui-li-has-alt";
- <div data-role="tokentextarea" data-link="fileName.html" data-dom-cache="true">
- </div>
-*/
-/**
- @event select
- The select event is fired when a token text area widget button is selected:
+ last = a.last();
+ splittheme = listsplittheme || last.jqmData( "theme" ) || o.splitTheme;
- <div data-role="tokentextarea">
- </div>
- $(".selector").on("select", function(event, ui)
- {
- // Handle the select event
- });
-*/
-/**
- @event add (@since Tizen 2.1 deprecated, You can still use this event. But not recommended.)
- The add event is fired when a token text area widget button is created:
+ last.appendTo(item)
+ .attr( "title", last.getEncodedText() )
+ .addClass( "ui-li-link-alt" )
+ .empty()
+ .buttonMarkup({
+ shadow: false,
+ corners: false,
+ theme: itemTheme,
+ icon: false,
+ iconpos: false
+ })
+ .find( ".ui-btn-inner" )
+ .append(
+ $( "<span />" ).buttonMarkup({
+ shadow: true,
+ corners: true,
+ theme: splittheme,
+ iconpos: "notext",
+ icon: listspliticon || last.jqmData( "icon" ) || o.splitIcon
+ })
+ );
+ }
+ } else if ( item.jqmData( "role" ) === "list-divider" ) {
- <div data-role="tokentextarea">
- </div>
- $(".selector").on("add", function(event, ui)
- {
- // Handle the add event
- });
-*/
-/**
- @event remove (@since Tizen 2.1 deprecated, You can still use this event. But not recommended.)
- The remove event is fired when a token text area widget button is removed:
- Restriction : "remove" event works under only "bind" event handling.
+ itemClass += " ui-li-divider ui-btn ui-bar-" + dividertheme;
+ item.attr( "role", "heading" );
- <div data-role="tokentextarea">
- </div>
- $(".selector").bind("remove", function(event, ui)
- {
- // Handle the remove event
- });
-*/
-/**
- @method destroy
- The destroy method is used to remove in the current widget all the new DOM elements that you have created.
+ //reset counter when a divider heading is encountered
+ if ( counter ) {
+ counter = 1;
+ }
- <div data-role="tokentextarea">
- </div>
- $(".selector").tokentextarea("destroy");
+ } else {
+ itemClass += " ui-li-static ui-body-" + itemTheme;
+ }
+ }
- @since Tizen2.0
-*/
-/**
- @method inputText
- The inputText method is used to manage the widget input box text. If no parameter is set, the method gets the input box text. If a parameter is set, the parameter text is set in the input box.
-
- <div data-role="tokentextarea">
- </div>
- $(".selector").tokentextarea("inputText", [text]);
-*/
-/**
- @method select
- The select method is used to select a token text area widget button based on its index value. If no index value is defined, the method returns the string of the selected block. If there are no buttons present in the widget, the method returns null.
+ if ( counter && itemClass.indexOf( "ui-li-divider" ) < 0 ) {
+ countParent = item.is( ".ui-li-static:first" ) ? item : item.find( ".ui-link-inherit" );
- <div data-role="tokentextarea">
- </div>
- $(".selector").tokentextarea("select", [index]);
-*/
-/**
- @method add
- The add method is used to add a new token text area widget button with the specified label text at the specified index position. If the index parameter is not defined, the widget button is added at the bottom of the list. For example, the $(".selector").tokentextarea("add", "Tizen", 2) method call creates a new widget button labeled 'Tizen' at the third position in the widget.
+ countParent.addClass( "ui-li-jsnumbering" )
+ .prepend( "<span class='ui-li-dec'>" + (counter++) + ". </span>" );
+ }
- <div data-role="tokentextarea">
- </div>
- $(".selector").tokentextarea("add", [text], [index]);
-*/
-/**
- @method remove
- The remove method is used to remove a token text area widget button at the specified index position. If the parameter is not defined, all the widget buttons are removed.
+ item.add( item.children( ".ui-btn-inner" ) ).addClass( itemClass );
- <div data-role="tokentextarea">
- </div>
- $(".selector").tokentextarea("remove", [index]);
-*/
-/**
- @method length
- The length method is used to retrieve the number of buttons in the token text area widget:
- <div data-role="tokentextarea">
- </div>
- $(".selector").tokentextarea("length");
-*/
-/**
- @method focusIn
- The focusIn method is used to set the focus status to "focus in". This focus state enables the user to add or remove buttons in the token text area widget.
+ self._itemApply( $list, item );
+ }
- <div data-role="tokentextarea">
- </div>
- $(".selector").tokentextarea("focusIn");
-*/
-/**
- @method focusOut
- The focusOut method is used to set the focus status to "focus out". In this focus state, the user cannot manage the buttons in the widget, all the buttons are removed, and a message is displayed.
+ this._refreshCorners( create );
+ },
- <div data-role="tokentextarea">
- </div>
- $(".selector").tokentextarea("focusOut");
-*/
-( function ( $, window, document, undefined ) {
- $.widget( "tizen.tokentextarea", $.mobile.widget, {
- _focusStatus : null,
- _items : null,
- _viewWidth : 0,
- _reservedWidth : 0,
- _currentWidth : 0,
- _fontSize : 0,
- _anchorWidth : 0,
- _labelWidth : 0,
- _marginWidth : 0,
- options : {
- label : "To : ",
- link : null,
- description : "+ {0}"
+ //create a string for ID/subpage url creation
+ _idStringEscape: function ( str ) {
+ return str.replace(/\W/g , "-");
},
- _create : function () {
- var self = this,
- $view = this.element,
- role = $view.jqmData( "role" ),
- option = this.options,
- className = "ui-tokentextarea-link",
- inputbox = $( document.createElement( "input" ) ),
- labeltag = $( document.createElement( "span" ) ),
- moreBlock = $( document.createElement( "a" ) );
+ // ?
+ // this virtuallistview object
+ _createSubPages: function () {
+ var parentList = this.element,
+ parentPage = parentList.closest( ".ui-page" ),
+ parentUrl = parentPage.jqmData( "url" ),
+ parentId = parentUrl || parentPage[ 0 ][ $.expando ],
+ parentListId = parentList.attr( "id" ),
+ o = this.options,
+ dns = "data-" + $.mobile.ns,
+ self = this,
+ persistentFooterID = parentPage.find( ":jqmData(role='footer')" ).jqmData( "id" ),
+ hasSubPages,
+ newRemove;
- $view.hide().empty().addClass( "ui-" + role );
+ if ( typeof listCountPerPage[ parentId ] === "undefined" ) {
+ listCountPerPage[ parentId ] = -1;
+ }
- // create a label tag.
- $( labeltag ).text( option.label ).addClass( "ui-tokentextarea-label" ).attr( "tabindex", 0 );
- $view.append( labeltag );
+ parentListId = parentListId || ++listCountPerPage[ parentId ];
- // create a input tag
- $( inputbox ).addClass( "ui-tokentextarea-input ui-tokentextarea-input-visible ui-input-text ui-body-s" ).attr( "role", "textbox" );
- $view.append( inputbox );
+ $( parentList.find( "li>ul, li>ol" ).toArray().reverse() ).each(function ( i ) {
+ var self = this,
+ list = $( this ),
+ listId = list.attr( "id" ) || parentListId + "-" + i,
+ parent = list.parent(),
+ nodeEls,
+ title = nodeEls.first().getEncodedText(),//url limits to first 30 chars of text
+ id = ( parentUrl || "" ) + "&" + $.mobile.subPageUrlKey + "=" + listId,
+ theme = list.jqmData( "theme" ) || o.theme,
+ countTheme = list.jqmData( "counttheme" ) || parentList.jqmData( "counttheme" ) || o.countTheme,
+ newPage,
+ anchor;
- // create a anchor tag.
- if ( option.link === null || $.trim( option.link ).length < 1 || $( option.link ).length === 0 ) {
- className += "-dim";
- }
- $( moreBlock ).attr( "data-role", "button" )
- .buttonMarkup( {
- inline: true,
- icon: "plus",
- style: "circle"
- })
- .attr( { "href" : $.trim( option.link ), "tabindex" : 0 } )
- .addClass( "ui-tokentextarea-link-base" )
- .addClass( className )
- .find( "span.ui-btn-text" )
- .text( "Add recipient" );
+ nodeEls = $( list.prevAll().toArray().reverse() );
+ nodeEls = nodeEls.length ? nodeEls : $( "<span>" + $.trim( parent.contents()[ 0 ].nodeValue ) + "</span>" );
- // append default htmlelements to main widget.
- $view.append( moreBlock );
+ //define hasSubPages for use in later removal
+ hasSubPages = true;
- // bind a event
- this._bindEvents();
- self._focusStatus = "init";
- // display widget
- $view.show();
+ newPage = list.detach()
+ .wrap( "<div " + dns + "role='page' " + dns + "url='" + id + "' " + dns + "theme='" + theme + "' " + dns + "count-theme='" + countTheme + "'><div " + dns + "role='content'></div></div>" )
+ .parent()
+ .before( "<div " + dns + "role='header' " + dns + "theme='" + o.headerTheme + "'><div class='ui-title'>" + title + "</div></div>" )
+ .after( persistentFooterID ? $( "<div " + dns + "role='footer' " + dns + "id='" + persistentFooterID + "'>" ) : "" )
+ .parent()
+ .appendTo( $.mobile.pageContainer );
- // assign global variables
- self._viewWidth = $view.innerWidth();
- self._reservedWidth += self._calcBlockWidth( moreBlock );
- self._reservedWidth += self._calcBlockWidth( labeltag );
- self._fontSize = parseInt( $( moreBlock ).css( "font-size" ), 10 );
- self._currentWidth = self._reservedWidth;
- self._modifyInputBoxWidth();
- },
+ newPage.page();
- // bind events
- _bindEvents : function () {
- var self = this,
- $view = self.element,
- option = self.options,
- inputbox = $view.find( ".ui-tokentextarea-input" ),
- moreBlock = $view.find( ".ui-tokentextarea-link-base" );
+ anchor = parent.find('a:first');
- // delegate a event to HTMLDivElement(each block).
- $view.delegate( "div", "click", function ( event ) {
- if ( $( this ).hasClass( "ui-tokentextarea-sblock" ) ) {
- // If block is selected, it will be removed.
- self._removeTextBlock();
+ if ( !anchor.length ) {
+ anchor = $( "<a/>" ).html( nodeEls || title ).prependTo( parent.empty() );
}
- var lockBlock = $view.find( "div.ui-tokentextarea-sblock" );
- if ( typeof lockBlock !== "undefined" ) {
- lockBlock.removeClass( "ui-tokentextarea-sblock" ).addClass( "ui-tokentextarea-block" );
- }
- $( this ).removeClass( "ui-tokentextarea-block" ).addClass( "ui-tokentextarea-sblock" );
- $view.trigger( "select" );
- });
+ anchor.attr( "href", "#" + id );
- inputbox.bind( "keyup", function ( event ) {
- // 8 : backspace
- // 13 : Enter
- // 186 : semi-colon
- // 188 : comma
- var keyValue = event.keyCode,
- valueString = $( inputbox ).val(),
- valueStrings = [],
- index,
- isSeparator = false;
+ }).virtuallistview();
- if ( keyValue === 8 ) {
- if ( valueString.length === 0 ) {
- self._validateTargetBlock();
- }
- } else if ( keyValue === 13 || keyValue === 186 || keyValue === 188 ) {
- if ( valueString.length !== 0 ) {
- // split content by separators(',', ';')
- valueStrings = valueString.split ( /[,;]/ );
- for ( index = 0; index < valueStrings.length; index++ ) {
- if ( valueStrings[index].length !== 0 && valueStrings[index].replace( /\s/g, "" ).length !== 0 ) {
- self._addTextBlock( valueStrings[index] );
- }
+ // on pagehide, remove any nested pages along with the parent page, as long as they aren't active
+ // and aren't embedded
+ if ( hasSubPages &&
+ parentPage.is( ":jqmData(external-page='true')" ) &&
+ parentPage.data( "page" ).options.domCache === false ) {
+
+ newRemove = function ( e, ui ) {
+ var nextPage = ui.nextPage, npURL;
+
+ if ( ui.nextPage ) {
+ npURL = nextPage.jqmData( "url" );
+ if ( npURL.indexOf( parentUrl + "&" + $.mobile.subPageUrlKey ) !== 0 ) {
+ self.childPages().remove();
+ parentPage.remove();
}
}
- inputbox.val( "" );
- isSeparator = true;
- } else {
- self._unlockTextBlock();
- }
+ };
- return !isSeparator;
- });
+ // unbind the original page remove and replace with our specialized version
+ parentPage
+ .unbind( "pagehide.remove" )
+ .bind( "pagehide.remove", newRemove );
+ }
+ },
- moreBlock.click( function () {
- if ( $( moreBlock ).hasClass( "ui-tokentextarea-link-dim" ) ) {
- return;
- }
+ // TODO sort out a better way to track sub pages of the virtuallistview this is brittle
+ childPages: function () {
+ var parentUrl = this.parentPage.jqmData( "url" );
- $( inputbox ).removeClass( "ui-tokentextarea-input-visible" ).addClass( "ui-tokentextarea-input-invisible" );
+ return $( ":jqmData(url^='" + parentUrl + "&" + $.mobile.subPageUrlKey + "')" );
+ }
+ });
- $.mobile.changePage( option.link, {
- transition: "slide",
- reverse: false,
- changeHash: false
- });
- });
+ //auto self-init widgets
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $( $.tizen.virtuallistview.prototype.options.initSelector, e.target ).virtuallistview();
+ });
- $( document ).bind( "pagechange.mbe", function ( event ) {
- if ( $view.innerWidth() === 0 ) {
- return ;
- }
- self.refresh();
- $( inputbox ).removeClass( "ui-tokentextarea-input-invisible" ).addClass( "ui-tokentextarea-input-visible" );
- });
+} ( jQuery ) );
- $view.bind( "click", function ( event ) {
- if ( self._focusStatus === "focusOut" ) {
- self.focusIn();
- }
- });
- },
- // create a textbutton and append this button to parent layer.
- // @param arg1 : string
- // @param arg2 : index
- _addTextBlock : function ( messages, blockIndex ) {
- if ( arguments.length === 0 ) {
- return;
- }
- if ( !messages ) {
- return ;
- }
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Author: Kangsik Kim <kangsik81.kim@samsung.com>
+ * Minkyeong Kim <minkyeong.kim@samsung.com>
+*/
- var self = this,
- $view = self.element,
- content = messages,
- index = blockIndex,
- blocks = null,
- textBlock = null;
+/**
+ * The TokenTextArea widget changes a text item to a button. It can be comprised of a number of button widgets.
+ * When a user types text and the text gets a specific event to change from a text to a button,
+ * the input text is changed to a TokenTextArea widget.
+ * A user can add the TokenTextArea widget to a contact list, email list, or another list.
+ * The typical use of this widget is composing a number of contacts or phone numbers in a specific area of the screen.
+ *
+ * HTML Attributes:
+ *
+ * data-link : Represents the id of the page or the URL of other HTML file.
+ * The page contains data for the user, for example, an address book.
+ * If the value is null, anchor button doesn't work. (Default : null)
+ * data-label: Provide a label for a user-guide. (Default : 'To : ')
+ * data-description : This attribute is managing message format.
+ * This message is displayed when widget status was changed to 'focusout'. (Default : '+ {0}')
+ *
+ * APIs:
+ *
+ * inputtext ( [string] )
+ * : If argument is not exist, will get a string from inputbox.
+ * If argument is exist, will set a string to inputbox.
+ * select ( [number] )
+ * : If no argument exists, gets a string of the selected block.
+ * If any button isn't selected on a token text area widget, this method returns "null" value.
+ * When a user call this method with an argument which is a number type,
+ * this method selects the button which is matched with the argument.
+ * add ( text, [number] )
+ * : If second argument does not exist, will insert to a new button at last position.
+ * Insert a new button at indexed position. The position is decided by the second argument.
+ * "index of position" means that the position of inserting a new button is decided by the second argument on "add" method.
+ * For example, if a user call the method like this "add("Tizen", 2)",
+ * new button labed "Tizen" will be inserted on the third position.
+ * remove ( [number] )
+ * : If no argument exists, all buttons are removed.
+ * Remove a button at indexed position.
+ * The position is decided by the second argument. (index: index of button)
+ * length ( void )
+ * : Get a number of buttons.
+ * foucsIn ( void )
+ * : This method change a status to 'focusin'.
+ * This status is able to manage a widget.
+ * focusOut ( void )
+ * : Changes the focus status to 'focus out'.
+ * The status is not able to manage a widget.
+ * All buttons that contained in the widget are removed and
+ * summarized message is displayed.
+ * destroy ( void )
+ * : Remove all of the new DOM elements for the current widget that you created.
+ *
+ * Events:
+ *
+ * select : Occur when a button is selected.
+ * add : Occur when new button is inserted. (@since Tizen 2.1 deprecated, You can still use this event. But not recommended.)
+ * remove : Occur when a button is removed. (@since Tizen 2.1 deprecated, You can still use this event. But not recommended.)
+ *
+ * Examples:
+ *
+ * <div data-role="tokentextarea" data-label="To : " data-link="#pageId" data-description="+ {0}">
+ * </div>
+ *
+ */
- if ( self._viewWidth === 0 ) {
- self._viewWidth = $view.innerWidth();
- }
- // Create a new text HTMLDivElement.
- textBlock = $( document.createElement( 'div' ) );
+/**
+ @class TokenTextArea
+ The TokenTextArea widget enables the user to enter text and convert it to a button. Each button that is created from entered text as a result of a change event forms a token text area widget. This widget is useful in composing an e-mail or SMS message to a group of addresses, each of which is a clickable item for more actions, such as copying, editing, or removing the address.
- textBlock.text( content ).addClass( "ui-tokentextarea-block" ).attr( { "aria-label" : "double tap to edit", "tabindex" : 0 } );
- textBlock.css( {'visibility': 'hidden'} );
+ To add a token text area widget to the application, use the following code:
+
+ <div data-role="tokentextarea" data-label="To : " data-link="#pageId">
+ </div>
+*/
+
+/**
+ @property {String} data-label
+ Sets a label as a guide for the user.
+ For example, while composing an e-mail message, the 'To : ' label is a guide for the user to enter e-mail addresses.
- blocks = $view.find( "div" );
- if ( index !== null && index <= blocks.length ) {
- $( blocks[index] ).before( textBlock );
- } else {
- $view.find( ".ui-tokentextarea-input" ).before( textBlock );
- }
+ <div data-role="tokentextarea" data-label="To : ">
+ </div>
+*/
- textBlock = self._ellipsisTextBlock( textBlock );
- textBlock.css( {'visibility': 'visible'} );
+/**
+ @property {String} data-decription
+ Manages the message format.
+ The message is displayed when the widget status changes to focus out
- self._modifyInputBoxWidth();
+ <div data-role="tokentextarea" data-description=" + {0}">
+ </div>
+ */
+/**
+ @property {String} data-link
+ Sets the ID of the page or the URL of other HTML file to which the button links.
+ If the data-link is set with the URL of other HTML file, the 'dom-cache' option of both page - a page containing a Tokentextarea and a page in the target HTML file - must be set as 'true'.
- textBlock.hide();
- textBlock.fadeIn( "fast", function () {
- self._currentWidth += self._calcBlockWidth( textBlock );
- $view.trigger( "add" );
- });
- },
+ <div data-role="tokentextarea" data-link="#pageId">
+ </div>
- _removeTextBlock : function () {
- var self = this,
- $view = this.element,
- lockBlock = $view.find( "div.ui-tokentextarea-sblock" ),
- _temp = null,
- _dummy = function () {};
+ <div data-role="tokentextarea" data-link="fileName.html" data-dom-cache="true">
+ </div>
+*/
+/**
+ @event select
+ The select event is fired when a token text area widget button is selected:
- if ( lockBlock !== null && lockBlock.length > 0 ) {
- self._currentWidth -= self._calcBlockWidth( lockBlock );
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").on("select", function(event, ui)
+ {
+ // Handle the select event
+ });
+*/
+/**
+ @event add (@since Tizen 2.1 deprecated, You can still use this event. But not recommended.)
+ The add event is fired when a token text area widget button is created:
- lockBlock.fadeOut( "fast", function () {
- lockBlock.remove();
- self._modifyInputBoxWidth();
- });
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").on("add", function(event, ui)
+ {
+ // Handle the add event
+ });
+*/
+/**
+ @event remove (@since Tizen 2.1 deprecated, You can still use this event. But not recommended.)
+ The remove event is fired when a token text area widget button is removed:
+ Restriction : "remove" event works under only "bind" event handling.
- this._eventRemoveCall = true;
- if ( $view[0].remove ) {
- _temp = $view[0].remove;
- $view[0].remove = _dummy;
- }
- $view.triggerHandler( "remove" );
- if ( _temp) {
- $view[0].remove = _temp;
- }
- this._eventRemoveCall = false;
- } else {
- $view.find( "div:last" ).removeClass( "ui-tokentextarea-block" ).addClass( "ui-tokentextarea-sblock" );
- }
- },
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").bind("remove", function(event, ui)
+ {
+ // Handle the remove event
+ });
+*/
+/**
+ @method destroy
+ The destroy method is used to remove in the current widget all the new DOM elements that you have created.
- _calcBlockWidth : function ( block ) {
- return $( block ).outerWidth( true );
- },
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").tokentextarea("destroy");
- _unlockTextBlock : function () {
- var $view = this.element,
- lockBlock = $view.find( "div.ui-tokentextarea-sblock" );
- if ( lockBlock ) {
- lockBlock.removeClass( "ui-tokentextarea-sblock" ).addClass( "ui-tokentextarea-block" );
- }
- },
+ @since Tizen2.0
+*/
+/**
+ @method inputText
+ The inputText method is used to manage the widget input box text. If no parameter is set, the method gets the input box text. If a parameter is set, the parameter text is set in the input box.
+
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").tokentextarea("inputText", [text]);
+*/
+/**
+ @method select
+ The select method is used to select a token text area widget button based on its index value. If no index value is defined, the method returns the string of the selected block. If there are no buttons present in the widget, the method returns null.
- // call when remove text block by backspace key.
- _validateTargetBlock : function () {
- var self = this,
- $view = self.element,
- lastBlock = $view.find( "div:last" ),
- tmpBlock = null;
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").tokentextarea("select", [index]);
+*/
+/**
+ @method add
+ The add method is used to add a new token text area widget button with the specified label text at the specified index position. If the index parameter is not defined, the widget button is added at the bottom of the list. For example, the $(".selector").tokentextarea("add", "Tizen", 2) method call creates a new widget button labeled 'Tizen' at the third position in the widget.
- if ( lastBlock.hasClass( "ui-tokentextarea-sblock" ) ) {
- self._removeTextBlock();
- } else {
- tmpBlock = $view.find( "div.ui-tokentextarea-sblock" );
- tmpBlock.removeClass( "ui-tokentextarea-sblock" ).addClass( "ui-tokentextarea-block" );
- lastBlock.removeClass( "ui-tokentextarea-block" ).addClass( "ui-tokentextarea-sblock" );
- }
- },
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").tokentextarea("add", [text], [index]);
+*/
+/**
+ @method remove
+ The remove method is used to remove a token text area widget button at the specified index position. If the parameter is not defined, all the widget buttons are removed.
- _ellipsisTextBlock : function ( textBlock ) {
- var self = this,
- $view = self.element,
- maxWidth = self._viewWidth / 2;
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").tokentextarea("remove", [index]);
+*/
+/**
+ @method length
+ The length method is used to retrieve the number of buttons in the token text area widget:
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").tokentextarea("length");
+*/
+/**
+ @method focusIn
+ The focusIn method is used to set the focus status to "focus in". This focus state enables the user to add or remove buttons in the token text area widget.
- if ( self._calcBlockWidth( textBlock ) > maxWidth ) {
- $( textBlock ).width( maxWidth - self._marginWidth );
- }
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").tokentextarea("focusIn");
+*/
+/**
+ @method focusOut
+ The focusOut method is used to set the focus status to "focus out". In this focus state, the user cannot manage the buttons in the widget, all the buttons are removed, and a message is displayed.
- return textBlock;
+ <div data-role="tokentextarea">
+ </div>
+ $(".selector").tokentextarea("focusOut");
+*/
+( function ( $, window, document, undefined ) {
+ $.widget( "tizen.tokentextarea", $.mobile.widget, {
+ _focusStatus : null,
+ _items : null,
+ _viewWidth : 0,
+ _reservedWidth : 0,
+ _currentWidth : 0,
+ _fontSize : 0,
+ _anchorWidth : 0,
+ _labelWidth : 0,
+ _marginWidth : 0,
+ options : {
+ label : "To : ",
+ link : null,
+ description : "+ {0}"
},
- _modifyInputBoxWidth : function () {
+ _create : function () {
var self = this,
- $view = self.element,
- margin = 0,
- labelWidth = 0,
- anchorWidth = 0,
- inputBoxWidth = 0,
- blocks = $view.find( "div" ),
- blockWidth = 0,
- index = 0,
- inputBoxMargin = 10,
- inputBox = $view.find( ".ui-tokentextarea-input" );
-
- if ( $view.width() === 0 ) {
- return;
- }
+ $view = this.element,
+ role = $view.jqmData( "role" ),
+ option = this.options,
+ className = "ui-tokentextarea-link",
+ inputbox = $( document.createElement( "input" ) ),
+ labeltag = $( document.createElement( "span" ) ),
+ moreBlock = $( document.createElement( "a" ) );
- if ( self._labelWidth === 0 ) {
- self._labelWidth = $view.find( ".ui-tokentextarea-label" ).outerWidth( true );
- self._anchorWidth = $view.find( ".ui-tokentextarea-link-base" ).outerWidth( true );
- self._marginWidth = parseInt( ( $( inputBox ).css( "margin-left" ) ), 10 );
- self._marginWidth += parseInt( ( $( inputBox ).css( "margin-right" ) ), 10 );
- self._viewWidth = $view.innerWidth();
- }
+ $view.hide().empty().addClass( "ui-" + role );
- margin = self._marginWidth;
- labelWidth = self._labelWidth;
- anchorWidth = self._anchorWidth;
- inputBoxWidth = self._viewWidth - labelWidth;
+ // create a label tag.
+ $( labeltag ).text( option.label ).addClass( "ui-tokentextarea-label" ).attr( "tabindex", 0 );
+ $view.append( labeltag );
- for ( index = 0; index < blocks.length; index += 1 ) {
- blockWidth = self._calcBlockWidth( blocks[index] );
+ // create a input tag
+ $( inputbox ).addClass( "ui-tokentextarea-input ui-tokentextarea-input-visible ui-input-text ui-body-s" ).attr( "role", "textbox" );
+ $view.append( inputbox );
- if ( blockWidth >= inputBoxWidth + anchorWidth ) {
- if ( blockWidth >= inputBoxWidth ) {
- inputBoxWidth = self._viewWidth - blockWidth;
- } else {
- inputBoxWidth = self._viewWidth;
- }
- } else {
- if ( blockWidth > inputBoxWidth ) {
- inputBoxWidth = self._viewWidth - blockWidth;
- } else {
- inputBoxWidth -= blockWidth;
- }
- }
+ // create a anchor tag.
+ if ( option.link === null || $.trim( option.link ).length < 1 || $( option.link ).length === 0 ) {
+ className += "-dim";
}
+ $( moreBlock ).attr( "data-role", "button" )
+ .buttonMarkup( {
+ inline: true,
+ icon: "plus",
+ style: "circle"
+ })
+ .attr( { "href" : $.trim( option.link ), "tabindex" : 0 } )
+ .addClass( "ui-tokentextarea-link-base" )
+ .addClass( className )
+ .find( "span.ui-btn-text" )
+ .text( "Add recipient" );
- inputBoxWidth -= margin;
- if ( inputBoxWidth < anchorWidth * 2 ) {
- inputBoxWidth = self._viewWidth - margin;
- }
- $( inputBox ).width( inputBoxWidth - anchorWidth - inputBoxMargin );
- },
+ // append default htmlelements to main widget.
+ $view.append( moreBlock );
- _stringFormat : function ( expression ) {
- var pattern = null,
- message = expression,
- i = 0;
- for ( i = 1; i < arguments.length; i += 1 ) {
- pattern = "{" + ( i - 1 ) + "}";
- message = message.replace( pattern, arguments[i] );
- }
- return message;
+ // bind a event
+ this._bindEvents();
+ self._focusStatus = "init";
+ // display widget
+ $view.show();
+
+ // assign global variables
+ self._viewWidth = $view.innerWidth();
+ self._reservedWidth += self._calcBlockWidth( moreBlock );
+ self._reservedWidth += self._calcBlockWidth( labeltag );
+ self._fontSize = parseInt( $( moreBlock ).css( "font-size" ), 10 );
+ self._currentWidth = self._reservedWidth;
+ self._modifyInputBoxWidth();
},
- _resizeBlocks : function () {
+ // bind events
+ _bindEvents : function () {
var self = this,
$view = self.element,
- blocks = $view.find( "div" ),
- index = 0;
+ option = self.options,
+ inputbox = $view.find( ".ui-tokentextarea-input" ),
+ moreBlock = $view.find( ".ui-tokentextarea-link-base" );
- for ( index = 0 ; index < blocks.length ; index += 1 ) {
- $( blocks[index] ).css( "width", "auto" );
- blocks[index] = self._ellipsisTextBlock( blocks[index] );
- }
- },
+ // delegate a event to HTMLDivElement(each block).
+ $view.delegate( "div", "click", function ( event ) {
+ if ( $( this ).hasClass( "ui-tokentextarea-sblock" ) ) {
+ // If block is selected, it will be removed.
+ self._removeTextBlock();
+ }
- //---------------------------------------------------- //
- // Public Method //
- //----------------------------------------------------//
- //
- // Focus In Event
- //
- focusIn : function () {
- if ( this._focusStatus === "focusIn" ) {
- return;
- }
+ var lockBlock = $view.find( "div.ui-tokentextarea-sblock" );
+ if ( typeof lockBlock !== "undefined" ) {
+ lockBlock.removeClass( "ui-tokentextarea-sblock" ).addClass( "ui-tokentextarea-block" );
+ }
+ $( this ).removeClass( "ui-tokentextarea-block" ).addClass( "ui-tokentextarea-sblock" );
+ $view.trigger( "select" );
+ });
- var $view = this.element;
+ inputbox.bind( "keyup", function ( event ) {
+ // 8 : backspace
+ // 13 : Enter
+ // 186 : semi-colon
+ // 188 : comma
+ var keyValue = event.keyCode,
+ valueString = $( inputbox ).val(),
+ valueStrings = [],
+ index,
+ isSeparator = false;
- $view.find( ".ui-tokentextarea-label" ).attr( "tabindex", 0 ).show();
- $view.find( ".ui-tokentextarea-desclabel" ).remove();
- $view.find( "div.ui-tokentextarea-sblock" ).removeClass( "ui-tokentextarea-sblock" ).addClass( "ui-tokentextarea-block" );
- $view.find( "div" ).attr( { "aria-label" : "double tap to edit", "tabindex" : 0 } ).show();
- $view.find( ".ui-tokentextarea-input" ).removeClass( "ui-tokentextarea-input-invisible" ).addClass( "ui-tokentextarea-input-visible" ).attr( "tabindex", 0 );
- $view.find( "a" ).attr( "tabindex", 0 ).show();
+ if ( keyValue === 8 ) {
+ if ( valueString.length === 0 ) {
+ self._validateTargetBlock();
+ }
+ } else if ( keyValue === 13 || keyValue === 186 || keyValue === 188 ) {
+ if ( valueString.length !== 0 ) {
+ // split content by separators(',', ';')
+ valueStrings = valueString.split ( /[,;]/ );
+ for ( index = 0; index < valueStrings.length; index++ ) {
+ if ( valueStrings[index].length !== 0 && valueStrings[index].replace( /\s/g, "" ).length !== 0 ) {
+ self._addTextBlock( valueStrings[index] );
+ }
+ }
+ }
+ inputbox.val( "" );
+ isSeparator = true;
+ } else {
+ self._unlockTextBlock();
+ }
- // change focus state.
- this._modifyInputBoxWidth();
- this._focusStatus = "focusIn";
- $view.removeClass( "ui-tokentextarea-focusout" ).addClass( "ui-tokentextarea-focusin" ).removeAttr( "tabindex" );
- $view.find( ".ui-tokentextarea-input" ).focus();
- },
+ return !isSeparator;
+ });
- focusOut : function () {
- if ( this._focusStatus === "focusOut" ) {
- return;
- }
+ moreBlock.click( function () {
+ if ( $( moreBlock ).hasClass( "ui-tokentextarea-link-dim" ) ) {
+ return;
+ }
- var self = this,
- $view = self.element,
- tempBlock = null,
- stateBlock = null,
- numBlock = null,
- statement = "",
- index = 0,
- lastIndex = 10,
- label = $view.find( ".ui-tokentextarea-label" ),
- more = $view.find( "span" ),
- blocks = $view.find( "div" ),
- currentWidth = $view.outerWidth( true ) - more.outerWidth( true ) - label.outerWidth( true ),
- blockWidth = 0;
+ $( inputbox ).removeClass( "ui-tokentextarea-input-visible" ).addClass( "ui-tokentextarea-input-invisible" );
- label.removeAttr( "tabindex" );
- $view.find( ".ui-tokentextarea-input" ).removeClass( "ui-tokentextarea-input-visible" ).addClass( "ui-tokentextarea-input-invisible" ).removeAttr( "tabindex" );
- $view.find( "a" ).removeAttr( "tabindex" ).hide();
- blocks.removeAttr( "aria-label" ).removeAttr( "tabindex" ).hide();
+ $.mobile.changePage( option.link, {
+ transition: "slide",
+ reverse: false,
+ changeHash: false
+ });
+ });
- currentWidth = currentWidth - self._reservedWidth;
+ $( document ).bind( "pagechange.mbe", function ( event ) {
+ if ( $view.innerWidth() === 0 ) {
+ return ;
+ }
+ self.refresh();
+ $( inputbox ).removeClass( "ui-tokentextarea-input-invisible" ).addClass( "ui-tokentextarea-input-visible" );
+ });
- for ( index = 0; index < blocks.length; index++ ) {
- blockWidth = $( blocks[index] ).outerWidth( true );
- if ( currentWidth - blockWidth <= 0 ) {
- lastIndex = index - 1;
- break;
+ $view.bind( "click", function ( event ) {
+ if ( self._focusStatus === "focusOut" ) {
+ self.focusIn();
}
+ });
+ },
- $( blocks[index] ).show();
- currentWidth -= blockWidth;
+ // create a textbutton and append this button to parent layer.
+ // @param arg1 : string
+ // @param arg2 : index
+ _addTextBlock : function ( messages, blockIndex ) {
+ if ( arguments.length === 0 ) {
+ return;
}
- if ( lastIndex !== blocks.length ) {
- statement = self._stringFormat( self.options.description, blocks.length - lastIndex - 1 );
- tempBlock = $( document.createElement( 'span' ) );
- tempBlock.addClass( "ui-tokentextarea-desclabel" ).attr( { "aria-label" : "more, double tap to edit", "tabindex" : "-1" } );
- stateBlock = $( document.createElement( 'span' ) ).text( statement ).attr( "aria-hidden", "true" );
- numBlock = $( document.createElement( 'span' ) ).text( blocks.length - lastIndex - 1 ).attr( "aria-label", "and" ).css( "visibility", "hidden" );
- tempBlock.append( stateBlock );
- tempBlock.append( numBlock );
- $( blocks[lastIndex] ).after( tempBlock );
+ if ( !messages ) {
+ return ;
}
- // update focus state
- this._focusStatus = "focusOut";
- $view.removeClass( "ui-tokentextarea-focusin" ).addClass( "ui-tokentextarea-focusout" ).attr( "tabindex", 0 );
- },
-
- inputText : function ( message ) {
- var $view = this.element;
+ var self = this,
+ $view = self.element,
+ content = messages,
+ index = blockIndex,
+ blocks = null,
+ textBlock = null;
- if ( arguments.length === 0 ) {
- return $view.find( ".ui-tokentextarea-input" ).val();
+ if ( self._viewWidth === 0 ) {
+ self._viewWidth = $view.innerWidth();
}
- $view.find( ".ui-tokentextarea-input" ).val( message );
- return message;
- },
- select : function ( index ) {
- var $view = this.element,
- lockBlock = null,
- blocks = null;
+ // Create a new text HTMLDivElement.
+ textBlock = $( document.createElement( 'div' ) );
- if ( this._focusStatus === "focusOut" ) {
- return;
- }
+ textBlock.text( content ).addClass( "ui-tokentextarea-block" ).attr( { "aria-label" : "double tap to edit", "tabindex" : 0 } );
+ textBlock.css( {'visibility': 'hidden'} );
- if ( arguments.length === 0 ) {
- // return a selected block.
- lockBlock = $view.find( "div.ui-tokentextarea-sblock" );
- if ( lockBlock ) {
- return lockBlock.text();
- }
- return null;
- }
- // 1. unlock all blocks.
- this._unlockTextBlock();
- // 2. select pointed block.
blocks = $view.find( "div" );
- if ( blocks.length > index ) {
- $( blocks[index] ).removeClass( "ui-tokentextarea-block" ).addClass( "ui-tokentextarea-sblock" );
- $view.trigger( "select" );
+ if ( index !== null && index <= blocks.length ) {
+ $( blocks[index] ).before( textBlock );
+ } else {
+ $view.find( ".ui-tokentextarea-input" ).before( textBlock );
}
- return null;
- },
- add : function ( message, position ) {
- if ( this._focusStatus === "focusOut" ) {
- return;
- }
+ textBlock = self._ellipsisTextBlock( textBlock );
+ textBlock.css( {'visibility': 'visible'} );
- this._addTextBlock( message, position );
+ self._modifyInputBoxWidth();
+
+ textBlock.hide();
+ textBlock.fadeIn( "fast", function () {
+ self._currentWidth += self._calcBlockWidth( textBlock );
+ $view.trigger( "add" );
+ });
},
- remove : function ( position ) {
+ _removeTextBlock : function () {
var self = this,
$view = this.element,
- blocks = $view.find( "div" ),
- index = 0,
+ lockBlock = $view.find( "div.ui-tokentextarea-sblock" ),
_temp = null,
_dummy = function () {};
- if ( this._focusStatus === "focusOut" ) {
- return;
- }
-
- if ( arguments.length === 0 ) {
- blocks.fadeOut( "fast", function () {
- blocks.remove();
- self._modifyInputBoxWidth();
- self._trigger( "clear" );
- });
- } else if ( !isNaN( position ) ) {
- // remove selected button
- index = ( ( position < blocks.length ) ? position : ( blocks.length - 1 ) );
+ if ( lockBlock !== null && lockBlock.length > 0 ) {
+ self._currentWidth -= self._calcBlockWidth( lockBlock );
- $( blocks[index] ).fadeOut( "fast", function () {
- $( blocks[index] ).remove();
+ lockBlock.fadeOut( "fast", function () {
+ lockBlock.remove();
self._modifyInputBoxWidth();
});
$view[0].remove = _temp;
}
this._eventRemoveCall = false;
+ } else {
+ $view.find( "div:last" ).removeClass( "ui-tokentextarea-block" ).addClass( "ui-tokentextarea-sblock" );
}
},
- length : function () {
- return this.element.find( "div" ).length;
- },
-
- refresh : function () {
- var self = this,
- viewWidth = this.element.innerWidth();
-
- if ( viewWidth && self._viewWidth !== viewWidth ) {
- self._viewWidth = viewWidth;
- }
- self._resizeBlocks();
- self._modifyInputBoxWidth();
+ _calcBlockWidth : function ( block ) {
+ return $( block ).outerWidth( true );
},
- destroy : function () {
+ _unlockTextBlock : function () {
var $view = this.element,
- _temp = null,
- _dummy = function () {};
-
- if ( this._eventRemoveCall ) {
- return;
- }
-
- $view.find( ".ui-tokentextarea-label" ).remove();
- $view.find( "div" ).undelegate( "click" ).remove();
- $view.find( "a" ).remove();
- $view.find( ".ui-tokentextarea-input" ).unbind( "keyup" ).remove();
-
- this._eventRemoveCall = true;
- if ( $view[0].remove ) {
- _temp = $view[0].remove;
- $view[0].remove = _dummy;
- }
- $view.remove();
- if ( _temp) {
- $view[0].remove = _temp;
+ lockBlock = $view.find( "div.ui-tokentextarea-sblock" );
+ if ( lockBlock ) {
+ lockBlock.removeClass( "ui-tokentextarea-sblock" ).addClass( "ui-tokentextarea-block" );
}
- this._eventRemoveCall = false;
-
- this._trigger( "destroy" );
- }
- });
-
- $( document ).bind( "pagecreate create", function () {
- $( ":jqmData(role='tokentextarea')" ).tokentextarea();
- });
-
- $( window ).bind( "resize", function () {
- $( ":jqmData(role='tokentextarea')" ).tokentextarea( "refresh" );
- });
-} ( jQuery, window, document ) );
-
-
-
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- */
-/*
-* jQuery Mobile Framework : "textinput" plugin for text inputs, textareas
-* Copyright (c) jQuery Project
-* Dual licensed under the MIT or GPL Version 2 licenses.
-* http://jquery.org/license
-* Authors: Jinhyuk Jun <jinhyuk.jun@samsung.com>
-* Wongi Lee <wongi11.lee@samsung.com>
-*/
-
-/**
- * Searchbar can be created using <input> element with type=search
- * <input type="search" name="search" id="search1" value="" />
- *
- * Searchbar can be inserted 3 cases
- * content : seachbar behave same as content element
- * header : searchbar placed below title(header), It doesn't move when scrolling page
- * inside optionheader : Searchbar placed inside optionheader, searchbar can be seen only expand optionheader
- *
- * Examples:
- *
- * HTML markup for creating Searchbar
- * <input type="search"/>
- *
- * How to make searchbar in content
- * <input type="search" name="" id="" value="" />
- *
- * How to make cancel button in searchbar
- * <div data-role="header" data-position ="fixed" >
- * <h1>Searchbar</h1>
- * <input type="search" data-cancel-btn=true name="" id="" value="" />
- * </div>
- *
- * How to make icon in front of searchbar
- * <div data-role="header" data-position ="fixed" >
- * <h1>Searchbar</h1>
- * <input type="search" data-icon="call" name="" id="" value="" />
- * </div>
-*/
-
-/**
- @class SearchBar
- The search bar widget is used to search for page content. This widget can be placed in the header, option header, or page content.
-
- To add a search bar widget to the application, use the following code:
-
- <label for="search-basic">Search Input:</label>
- <input type="search" name="search" id="searc-basic" value="" data-mini="true" />
-
- Tizen supports many search bar options as described in the jQueryMobile documentation for search bar options.
- The search bar can define callbacks for events as described in the jQueryMobile documentation for search bar events.
- You can use methods with the search bar as described in the jQueryMobile documentation for search bar methods.
-*/
-
-(function ( $, undefined ) {
-
- $.widget( "tizen.searchbar", $.mobile.widget, {
- options: {
- theme: null,
- initSelector: "input[type='search'],:jqmData(type='search'), input[type='tizen-search'],:jqmData(type='tizen-search')"
},
- _create: function () {
- var input = this.element,
- o = this.options,
- theme = o.theme || $.mobile.getInheritedTheme( this.element, "c" ),
- themeclass = " ui-body-" + theme,
- focusedEl,
- clearbtn,
- cancelbtn,
- defaultText,
- defaultTextClass,
- trimedText,
- newClassName,
- newStyle,
- newDiv,
- searchimage,
- inputedText,
- useCancelBtn = false,
- frontIcon = false;
-
- $( "label[for='" + input.attr( "id" ) + "']" ).addClass( "ui-input-text" );
-
- if ( typeof input[0].autocorrect !== "undefined" && !$.support.touchOverflow ) {
- // Set the attribute instead of the property just in case there
- // is code that attempts to make modifications via HTML.
- input[0].setAttribute( "autocorrect", "off" );
- input[0].setAttribute( "autocomplete", "off" );
- }
-
- focusedEl = input.wrap( "<div class='ui-input-search ui-shadow-inset ui-corner-all ui-btn-shadow" + themeclass + "'></div>" ).parent();
-
- if ( $( this.element ).data( "cancel-btn" ) === true ) {
- useCancelBtn = true;
- focusedEl.addClass( "ui-input-search-default" );
- }
- if ( $( this.element ).data( "icon" ) != undefined ) {
- frontIcon = true;
- focusedEl.addClass( "ui-search-bar-icon" );
- }
-
- clearbtn = $( "<a href='#' class='ui-input-clear' title='clear text'>clear text</a>" )
- .bind('click', function ( event ) {
- if ( input.attr( "disabled" ) == "disabled" ) {
- return false;
- }
- input
- .val( "" )
- .focus()
- .trigger( "change" );
- clearbtn.addClass( "ui-input-clear-hidden" );
- event.preventDefault();
- })
- .appendTo( focusedEl )
- .buttonMarkup({
- icon: "deleteSearch",
- iconpos: "notext",
- corners: true,
- shadow: true
- });
-
- function toggleClear() {
- setTimeout(function () {
- clearbtn.toggleClass( "ui-input-clear-hidden", !input.val() );
- }, 0);
- }
-
- function showCancel() {
- focusedEl
- .addClass( "ui-input-search-default" )
- .removeClass( "ui-input-search-wide" );
- cancelbtn
- .addClass( "ui-btn-cancel-show" )
- .removeClass( "ui-btn-cancel-hide" );
- }
+ // call when remove text block by backspace key.
+ _validateTargetBlock : function () {
+ var self = this,
+ $view = self.element,
+ lastBlock = $view.find( "div:last" ),
+ tmpBlock = null;
- function hideCancel() {
- focusedEl
- .addClass( "ui-input-search-wide" )
- .removeClass( "ui-input-search-default" );
- cancelbtn
- .addClass( "ui-btn-cancel-hide" )
- .removeClass( "ui-btn-cancel-show" );
- toggleClear();
+ if ( lastBlock.hasClass( "ui-tokentextarea-sblock" ) ) {
+ self._removeTextBlock();
+ } else {
+ tmpBlock = $view.find( "div.ui-tokentextarea-sblock" );
+ tmpBlock.removeClass( "ui-tokentextarea-sblock" ).addClass( "ui-tokentextarea-block" );
+ lastBlock.removeClass( "ui-tokentextarea-block" ).addClass( "ui-tokentextarea-sblock" );
}
+ },
- function makeFrontIcon() {
- var IconStyle = $( input ).jqmData( "icon" ),
- frontIcon = $( "<div data-role='button' data-style='circle'></div>" );
+ _ellipsisTextBlock : function ( textBlock ) {
+ var self = this,
+ $view = self.element,
+ maxWidth = self._viewWidth / 2;
- frontIcon
- .appendTo( focusedEl.parent() )
- .buttonMarkup( {
- icon: IconStyle,
- iconpos: "notext",
- corners: true,
- shadow: true
- } );
- frontIcon.addClass( "ui-btn-search-front-icon" );
+ if ( self._calcBlockWidth( textBlock ) > maxWidth ) {
+ $( textBlock ).width( maxWidth - self._marginWidth );
}
- toggleClear();
-
- input.bind( 'paste cut keyup focus change blur', toggleClear );
+ return textBlock;
+ },
- //SLP --start search bar with cancel button
- focusedEl.wrapAll( "<div class='input-search-bar'></div>" );
- searchimage = $("<div class='ui-image-search'></div>").appendTo( focusedEl );
+ _modifyInputBoxWidth : function () {
+ var self = this,
+ $view = self.element,
+ margin = 0,
+ labelWidth = 0,
+ anchorWidth = 0,
+ inputBoxWidth = 0,
+ blocks = $view.find( "div" ),
+ blockWidth = 0,
+ index = 0,
+ inputBoxMargin = 10,
+ inputBox = $view.find( ".ui-tokentextarea-input" );
- if ( frontIcon ) {
- makeFrontIcon();
+ if ( $view.width() === 0 ) {
+ return;
}
- if ( useCancelBtn ) {
- cancelbtn = $( "<div data-role='button' class='ui-input-cancel' title='clear text'>Cancel</div>" )
- .bind('click', function ( event ) {
- if ( input.attr( "disabled" ) == "disabled" ) {
- return false;
- }
- event.preventDefault();
- event.stopPropagation();
+ if ( self._labelWidth === 0 ) {
+ self._labelWidth = $view.find( ".ui-tokentextarea-label" ).outerWidth( true );
+ self._anchorWidth = $view.find( ".ui-tokentextarea-link-base" ).outerWidth( true );
+ self._marginWidth = parseInt( ( $( inputBox ).css( "margin-left" ) ), 10 );
+ self._marginWidth += parseInt( ( $( inputBox ).css( "margin-right" ) ), 10 );
+ self._viewWidth = $view.innerWidth();
+ }
- input
- .val( "" )
- .blur()
- .trigger( "change" );
+ margin = self._marginWidth;
+ labelWidth = self._labelWidth;
+ anchorWidth = self._anchorWidth;
+ inputBoxWidth = self._viewWidth - labelWidth;
- if ( useCancelBtn ) {
- hideCancel();
- }
- } )
- .appendTo( focusedEl.parent() )
- .buttonMarkup( {
- iconpos: "cancel",
- corners: true,
- shadow: true
- } );
- }
+ for ( index = 0; index < blocks.length; index += 1 ) {
+ blockWidth = self._calcBlockWidth( blocks[index] );
- // Input Focused
- input
- .focus( function () {
- if ( input.attr( "disabled" ) == "disabled" ) {
- return false;
+ if ( blockWidth >= inputBoxWidth + anchorWidth ) {
+ if ( blockWidth >= inputBoxWidth ) {
+ inputBoxWidth = self._viewWidth - blockWidth;
+ } else {
+ inputBoxWidth = self._viewWidth;
}
- if ( useCancelBtn ) {
- showCancel();
+ } else {
+ if ( blockWidth > inputBoxWidth ) {
+ inputBoxWidth = self._viewWidth - blockWidth;
+ } else {
+ inputBoxWidth -= blockWidth;
}
- focusedEl.addClass( $.mobile.focusClass );
- })
- .blur(function () {
- focusedEl.removeClass( $.mobile.focusClass );
- });
-
- // Default Text
- defaultText = input.jqmData( "default-text" );
-
- if ( ( defaultText != undefined ) && ( defaultText.length > 0 ) ) {
- defaultTextClass = "ui-input-default-text";
- trimedText = defaultText.replace(/\s/g, "");
-
- /* Make new class for default text string */
- newClassName = defaultTextClass + "-" + trimedText;
- newStyle = $( "<style>" + '.' + newClassName + ":after" + "{content:" + "'" + defaultText + "'" + "}" + "</style>" );
- $( 'html > head' ).append( newStyle );
+ }
+ }
- /* Make new empty <DIV> for default text */
- newDiv = $( "<div></div>" );
+ inputBoxWidth -= margin;
+ if ( inputBoxWidth < anchorWidth * 2 ) {
+ inputBoxWidth = self._viewWidth - margin;
+ }
+ $( inputBox ).width( inputBoxWidth - anchorWidth - inputBoxMargin );
+ },
- /* Add class and append new div */
- newDiv.addClass( defaultTextClass );
- newDiv.addClass( newClassName );
- newDiv.tap( function ( event ) {
- input.blur();
- input.focus();
- } );
+ _stringFormat : function ( expression ) {
+ var pattern = null,
+ message = expression,
+ i = 0;
+ for ( i = 1; i < arguments.length; i += 1 ) {
+ pattern = "{" + ( i - 1 ) + "}";
+ message = message.replace( pattern, arguments[i] );
+ }
+ return message;
+ },
- input.parent().append( newDiv );
+ _resizeBlocks : function () {
+ var self = this,
+ $view = self.element,
+ blocks = $view.find( "div" ),
+ index = 0;
- /* When focus, default text will be hide. */
- input
- .focus( function () {
- input.parent().find( "div.ui-input-default-text" ).addClass( "ui-input-default-hidden" );
- } )
- .blur( function () {
- var inputedText = input.val();
- if ( inputedText.length > 0 ) {
- input.parent().find( "div.ui-input-default-text" ).addClass( "ui-input-default-hidden" );
- } else {
- input.parent().find( "div.ui-input-default-text" ).removeClass( "ui-input-default-hidden" );
- }
- } );
+ for ( index = 0 ; index < blocks.length ; index += 1 ) {
+ $( blocks[index] ).css( "width", "auto" );
+ blocks[index] = self._ellipsisTextBlock( blocks[index] );
}
+ },
- if ( !input.attr("placeholder") ) {
- input.attr( "placeholder", "Search" );
+ //---------------------------------------------------- //
+ // Public Method //
+ //----------------------------------------------------//
+ //
+ // Focus In Event
+ //
+ focusIn : function () {
+ if ( this._focusStatus === "focusIn" ) {
+ return;
}
- },
- disable: function () {
- this.element.attr( "disabled", true );
- this.element.parent().addClass( "ui-disabled" );
- $( this.element ).blur();
- this.element.parent().parent().find(".ui-input-cancel").addClass( "ui-disabled" );
- },
+ var $view = this.element;
- enable: function () {
- this.element.attr( "disabled", false );
- this.element.parent().removeClass( "ui-disabled" );
- this.element.parent().parent().find(".ui-input-cancel").removeClass( "ui-disabled" );
- $( this.element ).focus();
- }
- } );
+ $view.find( ".ui-tokentextarea-label" ).attr( "tabindex", 0 ).show();
+ $view.find( ".ui-tokentextarea-desclabel" ).remove();
+ $view.find( "div.ui-tokentextarea-sblock" ).removeClass( "ui-tokentextarea-sblock" ).addClass( "ui-tokentextarea-block" );
+ $view.find( "div" ).attr( { "aria-label" : "double tap to edit", "tabindex" : 0 } ).show();
+ $view.find( ".ui-tokentextarea-input" ).removeClass( "ui-tokentextarea-input-invisible" ).addClass( "ui-tokentextarea-input-visible" ).attr( "tabindex", 0 );
+ $view.find( "a" ).attr( "tabindex", 0 ).show();
- //auto self-init widgets
- $( document ).bind( "pagecreate create", function ( e ) {
- $.tizen.searchbar.prototype.enhanceWithin( e.target );
- } );
+ // change focus state.
+ this._modifyInputBoxWidth();
+ this._focusStatus = "focusIn";
+ $view.removeClass( "ui-tokentextarea-focusout" ).addClass( "ui-tokentextarea-focusin" ).removeAttr( "tabindex" );
+ $view.find( ".ui-tokentextarea-input" ).focus();
+ },
-}( jQuery ) );
+ focusOut : function () {
+ if ( this._focusStatus === "focusOut" ) {
+ return;
+ }
+
+ var self = this,
+ $view = self.element,
+ tempBlock = null,
+ stateBlock = null,
+ numBlock = null,
+ statement = "",
+ index = 0,
+ lastIndex = 10,
+ label = $view.find( ".ui-tokentextarea-label" ),
+ more = $view.find( "span" ),
+ blocks = $view.find( "div" ),
+ currentWidth = $view.outerWidth( true ) - more.outerWidth( true ) - label.outerWidth( true ),
+ blockWidth = 0;
+ label.removeAttr( "tabindex" );
+ $view.find( ".ui-tokentextarea-input" ).removeClass( "ui-tokentextarea-input-visible" ).addClass( "ui-tokentextarea-input-invisible" ).removeAttr( "tabindex" );
+ $view.find( "a" ).removeAttr( "tabindex" ).hide();
+ blocks.removeAttr( "aria-label" ).removeAttr( "tabindex" ).hide();
+ currentWidth = currentWidth - self._reservedWidth;
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * Author: Kangsik Kim <kangsik81.kim@samsung.com>
- * Youmin Ha <youmin.ha@samsung.com>
-*/
+ for ( index = 0; index < blocks.length; index++ ) {
+ blockWidth = $( blocks[index] ).outerWidth( true );
+ if ( currentWidth - blockWidth <= 0 ) {
+ lastIndex = index - 1;
+ break;
+ }
-/**
- * In the web environment, it is challenging to display a large amount of data in a grid.
- * When an application needs to show, for example, image gallery with over 1,000 images,
- * the same enormous data must be inserted into a HTML document.
- * It takes a long time to display the data and manipulating DOM is complex.
- * The virtual grid widget supports storing unlimited data without performance issues
- * by reusing a limited number of grid elements.
- * The virtual grid widget is based on the jQuery.template plug-in
- * For more information, see jQuery.template.
- *
- * HTML Attributes:
- *
- * data-role: virtualgrid
- * data-template : Has the ID of the jQuery.template element.
- * jQuery.template for a virtual grid must be defined.
- * Style for template would use rem unit to support scalability.
- * data-direction : This option define the direction of the scroll.
- * You must choose one of the 'x' and 'y' (Default : y)
- * data-rotation : This option defines whether or not the circulation of the data.
- * If option is 'true' and scroll is reached the last data,
- * Widget will present the first data on the screen.
- * If option is ‘false’, Widget will operate like a scrollview.
- *
- * ID : <DIV> element that has "data-role=virtualgrid" must have ID attribute.
- *
- * APIs:
- *
- * create ( {
- * itemData: function ( idx ) { return json_obj; },
- * numItemData: number or function () { return number; },
- * cacheItemData: function ( minIdx, maxIdx ) {}
- * } )
- * : Create VirtualGrid widget. At this moment, _create method is called.
- * args : A collection of options
- * itemData: A function that returns JSON object for given index. Mandatory.
- * numItemData: Total number of itemData. Mandatory.
- * cacheItemData: Virtuallist will ask itemData between minIdx and maxIdx.
- * Developers can implement this function for preparing data.
- * Optional.
- *
- * centerTo ( selector )
- * : Center the particular item with the class name on the VirtualGrid's display area.;
- * i.e., this method selects an item in the data elements of grid using the class name and
- * moves the data elements inside the widget to display the row containing the selected item
- * in the middle of the screen.
- * If multiple items are matched with the class name, the first matched item will be selected.
- * This method is only available when "data-rotation" attribute is "true".
- *
- * resize ()
- * : Rearrange items to fit a new widget size.
- *
- * Events:
- * scrollstart : : This event triggers when a user begin to move the scroll on VirtualGrid.
- * scrollupdate : : This event triggers while a user moves the scroll on VirtualGrid.
- * scrollstop : This event triggers when a user stop the scroll on VirtualGrid.
- * select : This event triggers when a cell is selected.
- *
- * Examples:
- *
- * <script id="tizen-demo-namecard" type="text/x-jquery-tmpl">
- * <div class="ui-demo-namecard">
- * <div class="ui-demo-namecard-pic">
- * <img class="ui-demo-namecard-pic-img" src="${TEAM_LOGO}" />
- * </div>
- * <div class="ui-demo-namecard-contents">
- * <span class="name ui-li-text-main">${NAME}</span>
- * <span class="active ui-li-text-sub">${ACTIVE}</span>
- * <span class="from ui-li-text-sub">${FROM}</span>
- * </div>
- * </div>
- * </script>
- * <div id="virtualgrid-demo" data-role="virtualgrid" data-template="tizen-demo-namecard" >
- * </div>
- *
- */
+ $( blocks[index] ).show();
+ currentWidth -= blockWidth;
+ }
-// most of following codes are derived from jquery.mobile.scrollview.js
+ if ( lastIndex !== blocks.length ) {
+ statement = self._stringFormat( self.options.description, blocks.length - lastIndex - 1 );
+ tempBlock = $( document.createElement( 'span' ) );
+ tempBlock.addClass( "ui-tokentextarea-desclabel" ).attr( { "aria-label" : "more, double tap to edit", "tabindex" : "-1" } );
+ stateBlock = $( document.createElement( 'span' ) ).text( statement ).attr( "aria-hidden", "true" );
+ numBlock = $( document.createElement( 'span' ) ).text( blocks.length - lastIndex - 1 ).attr( "aria-label", "and" ).css( "visibility", "hidden" );
+ tempBlock.append( stateBlock );
+ tempBlock.append( numBlock );
+ $( blocks[lastIndex] ).after( tempBlock );
+ }
-/**
- @class VirtualGrid
- In the Web environment, it is challenging to display large amount of data in a list, such as displaying a contact list of over 1000 list items. It takes time to display the entire list in HTML and the DOM manipulation is complex.
+ // update focus state
+ this._focusStatus = "focusOut";
+ $view.removeClass( "ui-tokentextarea-focusin" ).addClass( "ui-tokentextarea-focusout" ).attr( "tabindex", 0 );
+ },
- The virtual grid widget is used to display a list of unlimited data elements on the screen for better performance. This widget displays the data in the grid format by reusing the existing grid control space. Virtual grids are based on the jQuery.template plugin as described in the jQuery documentation for jQuery.template plugin.
+ inputText : function ( message ) {
+ var $view = this.element;
- To add a virtual grid widget to the application, use the following code:
+ if ( arguments.length === 0 ) {
+ return $view.find( ".ui-tokentextarea-input" ).val();
+ }
+ $view.find( ".ui-tokentextarea-input" ).val( message );
+ return message;
+ },
- <script id="tizen-demo-namecard" type="text/x-jquery-tmpl">
- <div class="ui-demo-namecard">
- <div class="ui-demo-namecard-pic">
- <img class="ui-demo-namecard-pic-img" src="${TEAM_LOGO}" />
- </div>
- <div class="ui-demo-namecard-contents">
- <span class="name ui-li-text-main">${NAME}</span>
- </div>
- </div>
- </script>
- <div id="virtualgrid-demo" data-role="virtualgrid" data-template="tizen-demo-namecard">
- </div>
-*/
-/**
- @property {String} data-template
- Specifies the jQuery.template element ID.
- The jQuery.template must be defined. The template style can use rem units to support scalability.
-*/
-/**
- @property {String} data-direction
- Defines the scroll direction. The direction options are x (horizontal) and y (vertical).
- The default value is y.
-*/
-/**
- @property {Boolean} data-rotation
- Defines whether the data elements are displayed from the beginning of the list again once the end of file is reached.
- The default value is false.
-*/
-/**
- @event scrollstart
- The scrollstart event is fired when the user starts scrolling through the grid:
+ select : function ( index ) {
+ var $view = this.element,
+ lockBlock = null,
+ blocks = null;
- <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
- $(".selector").on("scrollstart", function(event, ui)
- {
- // Handle the scrollstart event
- });
-*/
-/**
- @event scrollupdate
- The scrollupdate event is fired when the user moves the scroll bar in the grid:
+ if ( this._focusStatus === "focusOut" ) {
+ return;
+ }
- <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
- $(".selector").on("scrollupdate", function(event, ui)
- {
- // Handle the scrollupdate event
- });
-*/
-/**
- @event scrollstop
- The scrollstop event is fired when the user stops scrolling:
+ if ( arguments.length === 0 ) {
+ // return a selected block.
+ lockBlock = $view.find( "div.ui-tokentextarea-sblock" );
+ if ( lockBlock ) {
+ return lockBlock.text();
+ }
+ return null;
+ }
+ // 1. unlock all blocks.
+ this._unlockTextBlock();
+ // 2. select pointed block.
+ blocks = $view.find( "div" );
+ if ( blocks.length > index ) {
+ $( blocks[index] ).removeClass( "ui-tokentextarea-block" ).addClass( "ui-tokentextarea-sblock" );
+ $view.trigger( "select" );
+ }
+ return null;
+ },
- <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
- $(".selector").on("scrollstop", function(event, ui)
- {
- // Handle the scrollstop event
- });
-*/
-/**
- @event select
- The select event is fired when a virtual grid cell is selected:
+ add : function ( message, position ) {
+ if ( this._focusStatus === "focusOut" ) {
+ return;
+ }
- <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
- $(".selector").on("select", function(event, ui)
- {
- // Handle the select event
- });
-*/
-/**
- @method create
- @param {function} itemData(index)
- @param {Number} numItemData
- @param {function} cacheItemData(minIndex, maxIndex)
- The create method is used to call the jQuery _create method. In the method parameters:
+ this._addTextBlock( message, position );
+ },
- function itemData(index) returns the JSON object matched with the given index. The index value is between 0 and numItemData-1.<br/>
- number numItemData or function numItemData() defines or returns a static number of items.<br/>
- function cacheItemData(minIndex, maxIndex) prepares the JSON data. This method is called before calling the itemData() method with index values between minIndex and maxIndex.<br/>
+ remove : function ( position ) {
+ var self = this,
+ $view = this.element,
+ blocks = $view.find( "div" ),
+ index = 0,
+ _temp = null,
+ _dummy = function () {};
- <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
- function itemData(idx)
- {
- return DATA[idx];
+ if ( this._focusStatus === "focusOut" ) {
+ return;
}
- function cacheItemData(minIdx, maxIdx)
- {
- // Prepare JSON data between minIdx and maxIdx
+
+ if ( arguments.length === 0 ) {
+ blocks.fadeOut( "fast", function () {
+ blocks.remove();
+ self._modifyInputBoxWidth();
+ self._trigger( "clear" );
+ });
+ } else if ( !isNaN( position ) ) {
+ // remove selected button
+ index = ( ( position < blocks.length ) ? position : ( blocks.length - 1 ) );
+
+ $( blocks[index] ).fadeOut( "fast", function () {
+ $( blocks[index] ).remove();
+ self._modifyInputBoxWidth();
+ });
+
+ this._eventRemoveCall = true;
+ if ( $view[0].remove ) {
+ _temp = $view[0].remove;
+ $view[0].remove = _dummy;
+ }
+ $view.triggerHandler( "remove" );
+ if ( _temp) {
+ $view[0].remove = _temp;
+ }
+ this._eventRemoveCall = false;
}
- var numItemData = DATA.length;
- $(".selector").virtualgrid("create",
- {
- itemData, numItemData, cacheItemData
- });
-*/
-/**
- @method centerTo
- The centerTo method is used to center the particular item with the class name on the VirtualGrid's display area. If multiple items are matched with the class name, the first matched item will be selected. This method is only available when "data-rotation" attribute is "true".
+ },
- <div data-role="virtualgrid" data-scroll="y" data-rotation="true" data-template="tizen-demo-namecard"></div>
- $(".selector").virtualgrid("centerTo", selector);
-*/
-/**
- @method resize
- The resize method is used to rearrange items to fit a new widget size. :
+ length : function () {
+ return this.element.find( "div" ).length;
+ },
- <div data-role="virtualgrid" data-scroll="y" data-template="tizen-demo-namecard"></div>
- $(".selector").virtualgrid("resize");
+ refresh : function () {
+ var self = this,
+ viewWidth = this.element.innerWidth();
- @since Tizen2.0
-*/
+ if ( viewWidth && self._viewWidth !== viewWidth ) {
+ self._viewWidth = viewWidth;
+ }
+ self._resizeBlocks();
+ self._modifyInputBoxWidth();
+ },
-( function ( $, window, document, undefined ) {
+ destroy : function () {
+ var $view = this.element,
+ _temp = null,
+ _dummy = function () {};
- function circularNum ( num, total ) {
- var n = num % total;
- if ( n < 0 ) {
- n = total + n;
- }
- return n;
- }
+ if ( this._eventRemoveCall ) {
+ return;
+ }
- function MomentumTracker ( options ) {
- this.options = $.extend( {}, options );
- this.easing = "easeOutQuad";
- this.reset();
- }
+ $view.find( ".ui-tokentextarea-label" ).remove();
+ $view.find( "div" ).undelegate( "click" ).remove();
+ $view.find( "a" ).remove();
+ $view.find( ".ui-tokentextarea-input" ).unbind( "keyup" ).remove();
- var tstates = {
- scrolling : 0,
- done : 1
- },
- _OVERFLOW_DIR_NONE = 0, /* ENUM */
- _OVERFLOW_DIR_UP = 1, /* ENUM */
- _OVERFLOW_DIR_DOWN = -1, /* ENUM */
- imgTagSrcAttrRE = /src\s*=\s*[\"\'][\w\/.]+.[A-z]+[\"\']/;
+ this._eventRemoveCall = true;
+ if ( $view[0].remove ) {
+ _temp = $view[0].remove;
+ $view[0].remove = _dummy;
+ }
+ $view.remove();
+ if ( _temp) {
+ $view[0].remove = _temp;
+ }
+ this._eventRemoveCall = false;
- function getCurrentTime () {
- return Date.now();
- }
+ this._trigger( "destroy" );
+ }
+ });
- $.extend( MomentumTracker.prototype, {
- start : function ( pos, speed, duration ) {
- this.state = ( speed !== 0 ) ? tstates.scrolling : tstates.done;
- this.pos = pos;
- this.speed = speed;
- this.duration = duration;
+ $( document ).bind( "pagecreate create", function () {
+ $( ":jqmData(role='tokentextarea')" ).tokentextarea();
+ });
- this.fromPos = 0;
- this.toPos = 0;
+ $( window ).bind( "resize", function () {
+ $( ":jqmData(role='tokentextarea')" ).tokentextarea( "refresh" );
+ });
+} ( jQuery, window, document ) );
- this.startTime = getCurrentTime();
- },
- reset : function () {
- this.state = tstates.done;
- this.pos = 0;
- this.speed = 0;
- this.duration = 0;
- },
- update : function () {
- var state = this.state, duration, elapsed, dx, x;
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Authors: Wonseop Kim ( wonseop.kim@samsung.com )
+*/
- if ( state == tstates.done ) {
- return this.pos;
- }
- duration = this.duration;
- elapsed = getCurrentTime () - this.startTime;
- elapsed = elapsed > duration ? duration : elapsed;
- dx = this.speed * ( 1 - $.easing[this.easing]( elapsed / duration, elapsed, 0, 1, duration ) );
- x = this.pos + ( dx / 2 );
- this.pos = x;
+/**
+ * "Handler" is a widget helping a user to scroll a window or panel.
+ * It is different from the scrollview feature in that the handler has a fixed size
+ * and disappears when a scroll size is smaller than a parent window's size.
+ * If the handler widget is activated, a scroll bar on the screen will be deactivated.
+ * The handler widget supports scrolling up and down and indicates the position of the scrolled window.
+ *
+ * HTML Attributes:
+ *
+ * data-handler : This attribute is indicating that whether enable.
+ * If you want to use, you will set 'true'.
+ * data-handler-theme : Set the widget theme ( optional )
+ *
+ * APIs:
+ *
+ * enableHandler ( boolean )
+ * : Get or set the use of handler widget.
+ * If the value is "true", it will be run handler widget.
+ * If the value is "false", it will be not run handler widget.
+ * If no value is specified, will act as a getter.
+ *
+ * Events:
+ *
+ * Examples:
+ *
+ * <div data-role="content" data-scroll="y" data-handler="true">
+ * <ul data-role="listview">
+ * <li data-role="list-divider">A</li>
+ * <li><a href="#">Adam Kinkaid</a></li>
+ * ...
+ * </ul>
+ * </div>
+ */
- if ( elapsed >= duration ) {
- this.state = tstates.done;
- }
- return this.pos;
- },
+/**
+ @class handler
+ The handler widget enables the user to vertically scroll through a page or panel using a fixed-size handle. The widget indicates the position of the scrolled window, and only appears on the screen if the parent page or panel's scroll size is larger than the screen size. <br/> To add a handler widget to the application, use the following code:
- done : function () {
- return this.state == tstates.done;
- },
+ <div data-role="content" data-scroll="y" data-handler="true">
+ <ul data-role="listview">
+ <li data-role="list-divider">A</li>
+ <li><a href="#">Adam Kinkaid</a></li>
+ ...
+ </ul>
+ </div>
+
+ You can use the enableHandler method with the handler widget to get (if no value is defined) or set the handler usage status. If the [enable] value is true, the handler is enabled; otherwise the handler is not used.
- getPosition : function () {
- return this.pos;
- }
- });
+ $("#.selector").scrollview("enableHandler", [enable]);
+*/
+/**
+ @property {Boolean} data-handler
+ Enables the handler widget. The value must be set to true.
+*/
+/**
+ @property {String} data-handler-theme
+ Sets the handler widget theme.
+*/
+( function ( $, document, undefined ) {
+ // The options of handler in scrollview
+ $.tizen.scrollview.prototype.options.handler = false;
+ $.tizen.scrollview.prototype.options.handlerTheme = "s";
- jQuery.widget ( "mobile.virtualgrid", jQuery.mobile.widget, {
- options : {
- // virtualgrid option
- template : "",
- direction : "y",
- rotation : false
- },
+ var originSetOption = $.tizen.scrollview.prototype._setOption,
+ createHandler = function ( target ) {
+ var $view = target,
+ prefix = "<div class=\"ui-handler ui-handler-direction-",
+ suffix = "\"><div class=\"ui-handler-track\"><div class=\"ui-handler-handle\"><div class=\"ui-handler-thumb\"></div></div></div></div>",
+ scrollview = $view.data( "scrollview" ),
+ options = scrollview.options,
+ direction = options.direction,
+ parentTheme = $.mobile.getInheritedTheme( scrollview, "s" ),
+ theme = options.theme || parentTheme,
+ isHorizontal = ( scrollview.options.direction === "x" ),
+ _$view = scrollview._$view,
+ _$clip = scrollview._$clip,
+ scrollbar = $view.find( ".ui-scrollbar" ),
+ handler = null,
+ handlerHandle = null,
+ viewLength = 0,
+ clipLength = 0,
+ handlerHeight = 0,
+ handlerMargin = 0,
+ trackLength = 0,
+ moveTimer,
+ isTouchable = $.support.touch,
+ dragStartEvt = ( isTouchable ? "touchstart" : "mousedown" ) + ".handler",
+ dragMoveEvt = ( isTouchable ? "touchmove" : "mousemove" ) + ".handler",
+ dragStopEvt = ( isTouchable ? "touchend" : "mouseup" ) + ".handler",
+ dragLeaveEvt = ( isTouchable ? " touchleave" : " mouseleave" ) + ".handler",
+ calculateLength = function () {
+ clipLength = ( isHorizontal ? _$clip.width() : _$clip.height() );
+ viewLength = ( isHorizontal ? _$view.width() : _$view.height() ) - clipLength;
+ trackLength = clipLength - handlerHeight - handlerMargin * 2;
+ },
+ setHanderPostion = function ( scrollPos ) {
+ var handlerPos = Math.round( ( isHorizontal ? scrollPos.x : scrollPos.y ) / viewLength * trackLength );
+ handlerHandle[0].style[ ( isHorizontal ? "left" : "top" ) ] = handlerPos + "px";
+ },
+ stopHandlerScroll = function () {
+ $( document ).unbind( ".handler" );
+ $view.moveData = null;
+ _$view.trigger( "scrollstop" );
+ };
+
+ if ( $view.find( ".ui-handler-handle" ).length !== 0 || typeof direction !== "string" ) {
+ return;
+ }
- create : function () {
- this._create.apply( this, arguments );
- },
+ handler = $( [ prefix, direction, suffix ].join( "" ) ).appendTo( $view.addClass( " ui-handler-" + theme ) );
+ handlerHandle = $view.find( ".ui-handler-handle" ).attr( {
+ "tabindex" : "0",
+ "aria-label" : ( isHorizontal ? "Horizontal handler, double tap and move to scroll" : "Verticalhandler, double tap and move to scroll" )
+ }).hide();
+ handlerHeight = ( isHorizontal ? handlerHandle.width() : handlerHandle.height() );
+ handlerMargin = ( isHorizontal ? parseInt( handler.css( "right" ), 10 ) : parseInt( handler.css( "bottom" ), 10 ) );
- _create : function ( args ) {
- $.extend( this, {
- // view
- _$view : null,
- _$clip : null,
- _$rows : null,
- _tracker : null,
- _viewSize : 0,
- _clipSize : 0,
- _cellSize : undefined,
- _currentItemCount : 0,
- _itemCount : 1,
- _inheritedSize : null,
+ $.extend( $view, {
+ moveData : null
+ });
- // timer
- _timerInterval : 0,
- _timerID : 0,
- _timerCB : null,
- _lastMove : null,
+ // handler drag
+ handlerHandle.bind( dragStartEvt, {
+ e : handlerHandle[0]
+ }, function ( event ) {
+ scrollview._stopMScroll();
- // Data
- _itemData : function ( idx ) { return null; },
- _numItemData : 0,
- _cacheItemData : function ( minIdx, maxIdx ) { },
- _totalRowCnt : 0,
- _templateText : null,
- _maxViewSize : 0,
- _modifyViewPos : 0,
- _maxSizeExceptClip : 0,
- _maxSize : 0,
+ var target = event.data.e,
+ t = ( isTouchable ? event.originalEvent.targetTouches[0] : event );
- // axis - ( true : x , false : y )
- _direction : false,
- _didDrag : true,
- _reservedPos : 0,
- _scalableSize : 0,
- _eventPos : 0,
- _nextPos : 0,
- _movePos : 0,
- _lastY : 0,
- _speedY : 0,
- _lastX : 0,
- _speedX : 0,
- _rowsPerView : 0,
- _fragment : null,
+ target.style.opacity = 1.0;
- _filterRatio : 0.9,
+ $view.moveData = {
+ target : target,
+ X : parseInt( target.style.left, 10 ) || 0,
+ Y : parseInt( target.style.top, 10 ) || 0,
+ pX : t.pageX,
+ pY : t.pageY
+ };
+ calculateLength();
- _overflowStartPos : 0,
- _overflowDir : 0,
- _overflowMaxDragDist : 100
- });
+ _$view.trigger( "scrollstart" );
- var self = this,
- $dom = $( self.element ),
- opts = self.options,
- $item = null;
+ if ( !isTouchable ) {
+ event.preventDefault();
+ }
- // itemData
- // If mandatory options are not given, Do nothing.
- if ( !args ) {
- return ;
- }
+ $( document ).bind( dragMoveEvt, function ( event ) {
+ var moveData = $view.moveData,
+ target = moveData.target,
+ handlePos = 0,
+ scrollPos = 0,
+ t = ( isTouchable ? event.originalEvent.targetTouches[0] : event );
- if ( !self._loadData( args ) ) {
- return;
- }
+ handlePos = ( isHorizontal ? moveData.X + t.pageX - moveData.pX : moveData.Y + t.pageY - moveData.pY );
- // make a fragment.
- self._fragment = document.createDocumentFragment();
+ if ( handlePos < 0 ) {
+ handlePos = 0;
+ }
- // read defined properties(width and height) from dom element.
- self._inheritedSize = self._getinheritedSize( self.element );
+ if ( handlePos > trackLength ) {
+ handlePos = trackLength;
+ }
+ scrollPos = - Math.round( handlePos / trackLength * viewLength );
- // set a scroll direction.
- self._direction = opts.direction === 'x' ? true : false;
+ if ( isHorizontal ) {
+ scrollview._setScrollPosition( scrollPos, 0 );
+ target.style.left = handlePos + "px";
+ } else {
+ scrollview._setScrollPosition( 0, scrollPos );
+ target.style.top = handlePos + "px";
+ }
- // make view layer
- self._$clip = $dom.addClass( "ui-scrollview-clip" ).addClass( "ui-virtualgrid-view" );
- $item = $( document.createElement( "div" ) ).addClass( "ui-scrollview-view" );
- self._clipSize = self._calculateClipSize();
- self._$clip.append( $item );
- self._$view = $item;
- self._$clip.css( "overflow", "hidden" );
- self._$view.css( "overflow", "hidden" );
+ event.preventDefault();
+ }).bind( dragStopEvt + dragLeaveEvt, function ( event ) {
+ stopHandlerScroll();
+ });
+ });
- // inherit from scrollview widget.
- self._scrollView = $.tizen.scrollview.prototype;
- self._initScrollView();
+ _$view.bind( dragStopEvt, function ( event ) {
+ stopHandlerScroll();
+ });
- // create tracker.
- self._createTracker();
- self._makePositioned( self._$clip );
- self._timerInterval = 1000 / self.options.fps;
+ $view.bind( "scrollstart", function ( event ) {
+ if ( !scrollview.enableHandler() ) {
+ return;
+ }
- self._timerID = 0;
- self._timerCB = function () {
- self._handleMomentumScroll();
- };
- $dom.closest( ".ui-content" ).addClass( "ui-virtualgrid-content" ).css( "overflow", "hidden" );
+ calculateLength();
- // add event handler.
- self._addBehaviors();
+ if ( viewLength < 0 || clipLength < handlerHeight ) {
+ if ( scrollbar.is( ":hidden" ) ) {
+ scrollbar.show();
+ }
+ return;
+ }
- self._currentItemCount = 0;
- self._createOverflowArea();
- self._createScrollBar();
- self.refresh();
- },
+ if ( scrollbar.is( ":visible" ) ) {
+ scrollbar.hide();
+ }
- // The argument is checked for compliance with the specified format.
- // @param args : Object
- // @return boolean
- _loadData : function ( args ) {
- var self = this;
+ if ( moveTimer ) {
+ clearInterval( moveTimer );
+ moveTimer = undefined;
+ }
- if ( args.itemData && typeof args.itemData == 'function' ) {
- self._itemData = args.itemData;
- } else {
- return false;
- }
- if ( args.numItemData ) {
- if ( typeof args.numItemData == 'function' ) {
- self._numItemData = args.numItemData( );
- } else if ( typeof args.numItemData == 'number' ) {
- self._numItemData = args.numItemData;
- } else {
- return false;
+ handler.addClass( "ui-handler-visible" );
+ handlerHandle.stop( true, true )
+ .fadeIn();
+ }).bind( "scrollupdate", function ( event, data ) {
+ if ( !scrollview.enableHandler() || viewLength < 0 || clipLength < handlerHeight ) {
+ return;
}
- } else {
- return false;
- }
- self._getObjectNames( self._itemData( 0 ) );
- return true;
- },
- // Make up the first screen.
- _initLayout: function () {
- var self = this,
- opts = self.options,
- i,
- $row;
+ setHanderPostion( scrollview.getScrollPosition() );
+ }).bind( "scrollstop", function ( event ) {
+ if ( !scrollview.enableHandler() || viewLength < 0 || clipLength < handlerHeight ) {
+ return;
+ }
- for ( i = -1; i < self._rowsPerView + 1; i += 1 ) {
- $row = self._$rows[ circularNum( i, self._$rows.length ) ];
- self._$view.append( $row );
- }
- self._setElementTransform( -self._cellSize );
+ moveTimer = setInterval( function () {
+ setHanderPostion( scrollview.getScrollPosition() );
+ if ( !scrollview._gesture_timer ) {
+ clearInterval( moveTimer );
+ moveTimer = undefined;
+ }
+ }, 10 );
- self._replaceRow( self._$view[0].firstChild, self._totalRowCnt - 1 );
- if ( opts.rotation && self._rowsPerView >= self._totalRowCnt ) {
- self._replaceRow( self._$view[0].lastChild, 0 );
+ if ( scrollview._handlerTimer ) {
+ clearTimeout( scrollview._handlerTimer );
+ scrollview._handlerTimer = 0;
+ }
+ scrollview._handlerTimer = setTimeout( function () {
+ if ( scrollview._timerID === 0 && $view.moveData === null ) {
+ handlerHandle.stop( true, true )
+ .css( "opacity", 1.0 )
+ .fadeOut( function () {
+ handler.removeClass( "ui-handler-visible" );
+ });
+ scrollview._handlerTimer = 0;
+ }
+ }, 1000 );
+ }).bind( "mousewheel", function ( event ) {
+ handler.removeClass( "ui-handler-visible" );
+ setHanderPostion( scrollview.getScrollPosition() );
+ });
+ };
+
+ $.extend( $.tizen.scrollview.prototype, {
+ enableHandler: function ( enabled ) {
+ if ( typeof enabled === 'undefined' ) {
+ return this.options.handler;
}
- self._setViewSize();
- },
- _setViewSize : function () {
- var self = this,
- height = 0,
- width = 0;
+ this.options.handler = !!enabled;
+
+ var $view = this.element;
+ if ( this.options.handler ) {
+ if ( $view.find( ".ui-handler" ).length === 0 ) {
+ createHandler( $view );
+ }
- if ( self._direction ) {
- width = self._cellSize * ( self._rowsPerView + 2 );
- width = parseInt( width, 10 ) + 1;
- self._$view.width( width );
- self._viewSize = self._$view.width();
+ $view.find( ".ui-scrollbar" ).hide();
+ $view.find( ".ui-handler" ).show();
} else {
- self._$view.height( self._cellSize * ( self._rowsPerView + 2 ) );
- self._$clip.height( self._clipSize );
- self._viewSize = self._$view.height();
+ $view.find( ".ui-handler" ).removeClass( "ui-handler-visible" ).hide();
+ $view.find( ".ui-scrollbar" ).show();
}
},
- _getViewWidth : function () {
- var self = this;
- return self._maxSize;
+ _setHandlerTheme: function ( handlerTheme ) {
+ if ( !handlerTheme ) {
+ return;
+ }
+
+ var oldClass = "ui-handler-" + this.options.handlerTheme,
+ newClass = "ui-handler-" + handlerTheme;
+
+ this.element.removeClass( oldClass ).addClass( newClass );
+ this.options.handlerTheme = handlerTheme;
},
- _getViewHeight : function () {
- var self = this;
- return self._maxSize;
+ _setOption: function ( key, value ) {
+ switch ( key ) {
+ case "handler":
+ this.enableHandler( value );
+ break;
+ case "handlerTheme":
+ this._setHandlerTheme( value );
+ break;
+ default:
+ originSetOption.call( this, key, value );
+ }
},
- refresh : function () {
- var self = this,
- opts = self.options,
- width = 0,
- height = 0,
- $template = null;
+ _handlerTimer : 0
+ });
- $template = $( "#" + opts.template );
- if ( !$template ) {
- return ;
- }
- self._templateText = self._insertAriaAttrToTmpl( $template.text() );
+ $( document ).delegate( ":jqmData(scroll)", "scrollviewcreate", function () {
+ var widget = $( this );
+ if ( widget.attr( "data-" + $.mobile.ns + "scroll" ) === "none"
+ || widget.attr( "data-" + $.mobile.ns + "handler" ) !== "true" ) {
+ return;
+ }
+ widget.scrollview( "enableHandler", "true" );
+ });
+} ( jQuery, document ) );
- width = self._calculateClipWidth();
- height = self._calculateClipHeight();
- self._$view.width( width ).height( height );
- self._$clip.width( width ).height( height );
- self._clipSize = self._calculateClipSize();
- self._calculateColumnSize();
- self._initPageProperty();
- self._setScrollBarSize();
- },
- _initPageProperty : function () {
- var self = this,
- rowsPerView = 0,
- $child,
- columnCount = 0,
- totalRowCnt = 0,
- attributeName = self._direction ? "width" : "height";
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software" ),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Author: Minkyu Kang <mk7.kang@samsung.com>
+ * Author: Koeun Choi <koeun.choi@samsung.com>
+ */
- columnCount = self._calculateColumnCount();
+/*
+ * Progress widget
+ *
+ * HTML Attributes
+ *
+ * data-role: set to 'progress'.
+ * data-style: 'circle' or 'pending'.
+ *
+ * APIs
+ *
+ * show(): show the progress.
+ * hide(): hide the progress.
+ * running(boolean): start or stop the running.
+ *
+ * Events
+ *
+ * N/A
+ *
+ * Examples
+ *
+ * <li data-role="list-divider">Progress Pending</li>
+ * <li>
+ * <div data-role="progress" data-style="pending" id="pending"></div>
+ * </li>
+ * <li data-role="list-divider">Progress ~ing</li>
+ * <li>
+ * <div data-role="progress" data-style="circle" id="progress"></div>Loading..
+ * </li>
+ *
+ * $("#pending").progress( "running", true );
+ * $("#progress").progress( "running", true );
+ *
+ */
- totalRowCnt = parseInt( self._numItemData / columnCount, 10 );
- self._totalRowCnt = self._numItemData % columnCount === 0 ? totalRowCnt : totalRowCnt + 1;
- self._itemCount = columnCount;
+/**
+ @class Progress
+ The progress widget shows that an operation is in progress. <br/>To add a progress widget to the application, use the following code:
- if ( self._cellSize <= 0 ) {
- return ;
- }
+ <div data-role="progress" data-style="circle"></div>
+*/
+/**
+ @property {String} data-style
+ Sets the style of the progress widget. The style options are pending (pending progress style) and circle (circular progress status style).
+*/
+/**
+ @method running
+ The running method is used to set the current running state of the pending or circular progress widget:
- rowsPerView = self._clipSize / self._cellSize;
- rowsPerView = Math.ceil( rowsPerView );
- self._rowsPerView = parseInt( rowsPerView, 10 );
+ <div id="foo" data-role="progress" data-style="pending"></div>
+ $("#foo").progress("running", true);
+*/
+/**
+ @method show
+ The show method is used to show the pending or circular progress widget:
- $child = $( self._makeRows( rowsPerView + 2 ) );
- self._$view.append( $child.children() );
- self._$view.children().css( attributeName, self._cellSize + "px" );
- self._$rows = self._$view.children().detach();
+ <div id="foo" data-role="progress" data-style="pending"></div>
+ $("#foo").progress("show");
+*/
+/**
+ @method hide
+ The show method is used to hide the pending or circular progress widget:
- self._reservedPos = -self._cellSize;
- self._scalableSize = -self._cellSize;
+ <div id="foo" data-role="progress" data-style="pending"></div>
+ $("#foo").progress("hide");
+*/
- self._initLayout();
+(function ( $, window, undefined ) {
+ $.widget( "tizen.progress", $.mobile.widget, {
+ options: {
+ style: "circle",
+ running: false
+ },
- self._blockScroll = self._rowsPerView > self._totalRowCnt;
- self._maxSizeExceptClip = ( self._totalRowCnt - self._rowsPerView ) * self._cellSize;
- self._maxSize = self._totalRowCnt * self._cellSize;
- self._maxViewSize = ( self._rowsPerView ) * self._cellSize;
- self._modifyViewPos = -self._cellSize;
- if ( self._clipSize < self._maxViewSize ) {
- self._modifyViewPos = ( -self._cellSize ) + ( self._clipSize - self._maxViewSize );
+ show: function () {
+ $( this.element ).show();
+ },
+
+ hide: function () {
+ $( this.element ).hide();
+ },
+
+ _start: function () {
+ if ( !this.init ) {
+ $( this.element ).append( this.html );
+ this.init = true;
}
+
+ this.show();
+
+ $( this.element )
+ .find( ".ui-progress-" + this.options.style )
+ .addClass( this.runningClass );
},
- _getinheritedSize : function ( elem ) {
- var $target = $( elem ),
- height,
- width,
- NODETYPE = { ELEMENT_NODE : 1, TEXT_NODE : 3 },
- ret = {
- isDefinedWidth : false,
- isDefinedHeight : false,
- width : 0,
- height : 0
- };
+ _stop: function () {
+ $( this.element )
+ .find( ".ui-progress-" + this.options.style )
+ .removeClass( this.runningClass );
+ },
- while ( $target[0].nodeType === NODETYPE.ELEMENT_NODE && ( ret.isDefinedWidth === false || ret.isHeightDefined === false ) ) {
- height = $target[0].style.height;
- width = $target[0].style.width;
+ running: function ( running ) {
+ if ( running === undefined ) {
+ return this.options.running;
+ }
- if ( ret.isDefinedHeight === false && height !== "" ) {
- // Size was defined
- ret.isDefinedHeight = true;
- ret.height = parseInt( height, 10 );
- }
+ this._setOption( "running", running );
+ },
- if ( ret.isDefinedWidth === false && width !== "" ) {
- // Size was defined
- ret.isDefinedWidth = true;
- ret.width = parseInt( width, 10 );
- }
- $target = $target.parent();
- if ( $target.hasClass( "ui-content" ) ) {
- break;
+ _setOption: function ( key, value ) {
+ if ( key === "running" ) {
+ if ( typeof value !== "boolean" ) {
+ window.alert( "running value MUST be boolean type!" );
+ return;
}
+
+ this.options.running = value;
+ this._refresh();
}
- return ret;
},
- _resize : function () {
+ _refresh: function () {
+ if ( this.options.running ) {
+ this._start();
+ } else {
+ this._stop();
+ }
+ },
+
+ _create: function () {
var self = this,
- ret = null,
- rowsPerView = 0,
- itemCount = 0,
- totalRowCnt = 0,
- diffRowCnt = 0,
- clipSize = 0,
- prevcnt = 0,
- clipPosition = 0,
- rowsLength = 0,
- row = null,
- size = 0;
+ element = this.element,
+ style = element.jqmData( "style" ),
+ _html,
+ runningClass;
- if ( self._direction ) {
- size = self._calculateClipHeight();
- self._$view.height( size );
- self._$clip.height( size );
+ if ( style ) {
+ this.options.style = style;
} else {
- size = self._calculateClipWidth();
- self._$view.width( size );
- self._$clip.width( size );
+ style = this.options.style;
}
- itemCount = self._calculateColumnCount();
- if ( itemCount != self._itemCount ) {
- totalRowCnt = parseInt( self._numItemData / itemCount, 10 );
- self._totalRowCnt = self._numItemData % itemCount === 0 ? totalRowCnt : totalRowCnt + 1;
- prevcnt = self._itemCount;
- self._itemCount = itemCount;
- clipPosition = self._getClipPosition();
- self._$view.hide();
+ if ( style == "circle" ) {
+ $( this.element ).addClass("ui-progress-container-circle");
- diffRowCnt = self._replaceRows( itemCount, prevcnt, self._totalRowCnt, clipPosition );
- self._maxSizeExceptClip = ( self._totalRowCnt - self._rowsPerView ) * self._cellSize;
- self._maxSize = self._totalRowCnt * self._cellSize;
- self._scalableSize += ( -diffRowCnt ) * self._cellSize;
- self._reservedPos += ( -diffRowCnt ) * self._cellSize;
- self._setScrollBarSize();
- self._setScrollBarPosition( diffRowCnt );
+ _html = '<div class="ui-progress-circle"></div>';
+ } else if ( style === "pending" ) {
+ $( this.element ).addClass("ui-progressbar");
- self._$view.show();
+ _html = '<div class="ui-progressbar-bg">' +
+ '<div class="ui-progress-pending"></div>' +
+ '</div>';
}
- clipSize = self._calculateClipSize();
- if ( clipSize !== self._clipSize ) {
- rowsPerView = clipSize / self._cellSize;
- rowsPerView = parseInt( Math.ceil( rowsPerView ), 10 );
+ this.html = $( _html );
- if ( rowsPerView > self._rowsPerView ) {
- // increase row.
- self._increaseRow( rowsPerView - self._rowsPerView );
- } else if ( rowsPerView < self._rowsPerView ) {
- // decrease row.
- self._decreaseRow( self._rowsPerView - rowsPerView );
- }
- self._$rows = self._$view.children();
- self._$rows.sort( function ( a, b ) {
- return a.getAttribute( "row-index" ) - b.getAttribute( "row-index" );
- });
+ runningClass = "ui-progress-" + style + "-running";
- self._rowsPerView = rowsPerView;
- self._clipSize = clipSize;
- self._blockScroll = self._rowsPerView > self._totalRowCnt;
- self._maxSizeExceptClip = ( self._totalRowCnt - self._rowsPerView ) * self._cellSize;
- self._maxSize = self._totalRowCnt * self._cellSize;
- self._maxViewSize = ( self._rowsPerView ) * self._cellSize;
- if ( self._clipSize < self._maxViewSize ) {
- self._modifyViewPos = ( -self._cellSize ) + ( self._clipSize - self._maxViewSize );
- }
- if ( self._direction ) {
- self._$clip.width( self._clipSize );
- } else {
- self._$clip.height( self._clipSize );
- }
- self._setScrollBarSize();
- self._setScrollBarPosition( 0 );
- self._setViewSize();
+ $.extend( this, {
+ init: false,
+ runningClass: runningClass
+ } );
+
+ if ( style === "pending" ) {
+ $( this.element ).append( this.html );
+ this.init = true;
}
+
+ this._refresh();
+ }
+ } ); /* End of widget */
+
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $( e.target ).find( ":jqmData(role='progress')" ).progress();
+ } );
+}( jQuery, this ));
+
+
+
+/*
+ * This software is licensed under the MIT licence (as defined by the OSI at
+ * http://www.opensource.org/licenses/mit-license.php)
+ *
+ * ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2011 by Intel Corporation Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ */
+
+( function ($, undefined) {
+
+ $.widget( "tizen.triangle", $.tizen.widgetex, {
+ options: {
+ extraClass: "",
+ offset: null,
+ color: null,
+ location: "top",
+ initSelector: ":jqmData(role='triangle')"
},
- resize : function () {
- var self = this,
- height = 0,
- $virtualgrid = $( ".ui-virtualgrid-view" );
+ _create: function () {
+ var triangle = $( "<div></div>", {"class" : "ui-triangle"} );
- self._inheritedSize = self._getinheritedSize( self.element );
+ $.extend(this, {
+ _triangle: triangle
+ });
- if ( $virtualgrid.length !== 0 ) {
- self._resize();
- }
+ this.element.addClass( "ui-triangle-container" ).append( triangle );
},
- _initScrollView : function () {
- var self = this,
- oldDirection = self.options.direction;
- $.extend( self.options, self._scrollView.options );
- self.options.direction = oldDirection;
- self.options.moveThreshold = 10;
- self.options.showScrollBars = false;
- self._getScrollHierarchy = self._scrollView._getScrollHierarchy;
- self._makePositioned = self._scrollView._makePositioned;
- self._set_scrollbar_size = self._scrollView._set_scrollbar_size;
- self._setStyleTransform = self._scrollView._setElementTransform;
- self._hideOverflowIndicator = self._scrollView._hideOverflowIndicator;
- self._showOverflowIndicator = self._scrollView._showOverflowIndicator;
- self._setGestureScroll = self._scrollView._setGestureScroll;
+ _doCSS: function () {
+ var location = ( this.options.location || "top" ),
+ offsetCoord = ( ($.inArray(location, ["top", "bottom"]) === -1) ? "top" : "left"),
+ cssArg = {
+ "border-bottom-color" : "top" === location ? this.options.color : "transparent",
+ "border-top-color" : "bottom" === location ? this.options.color : "transparent",
+ "border-left-color" : "right" === location ? this.options.color : "transparent",
+ "border-right-color" : "left" === location ? this.options.color : "transparent"
+ };
+
+ cssArg[offsetCoord] = this.options.offset;
+
+ this._triangle.removeAttr( "style" ).css( cssArg );
},
- _createTracker : function () {
- var self = this;
+ _setOffset: function ( value ) {
+ this.options.offset = value;
+ this.element.attr( "data-" + ($.mobile.ns || "") + "offset", value );
+ this._doCSS();
+ },
- self._tracker = new MomentumTracker( self.options );
- if ( self._direction ) {
- self._hTracker = self._tracker;
- self._$clip.width( self._clipSize );
- } else {
- self._vTracker = self._tracker;
- self._$clip.height( self._clipSize );
- }
+ _setExtraClass: function ( value ) {
+ this._triangle.addClass( value );
+ this.options.extraClass = value;
+ this.element.attr( "data-" + ($.mobile.ns || "") + "extra-class", value );
},
- //----------------------------------------------------//
- // Overflow effect
- //----------------------------------------------------//
- _createOverflowArea : function () {
- var self = this,
- prefix = "<div class=\"ui-virtualgrid-overflow-indicator-",
- suffixTop = "-top\"></div>",
- suffixBottom = "-bottom\"></div>";
+ _setColor: function ( value ) {
+ this.options.color = value;
+ this.element.attr( "data-" + ($.mobile.ns || "") + "color", value );
+ this._doCSS();
+ },
- if ( self.options.rotation ) {
- return;
- }
+ _setLocation: function ( value ) {
+ this.element
+ .removeClass( "ui-triangle-container-" + this.options.location )
+ .addClass( "ui-triangle-container-" + value );
+ this._triangle
+ .removeClass( "ui-triangle-" + this.options.location )
+ .addClass( "ui-triangle-" + value );
+
+ this.options.location = value;
+ this.element.attr( "data-" + ($.mobile.ns || "") + "location", value );
+
+ this._doCSS();
+ }
+ });
+
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $($.tizen.triangle.prototype.options.initSelector, e.target)
+ .not(":jqmData(role='none'), :jqmData(role='nojs')")
+ .triangle();
+ });
+
+}(jQuery) );
+
+
+
+/**
+ * @class core
+ * loader.js
+ *
+ * Youmin Ha <youmin.ha@samsung.com>
+ *
+ *
+ */
+/*
+ Web UI scaling concept in Tizen Web UI
- if ( self._direction ) {
- self._overflowTop = $( prefix + "x" + suffixTop );
- self._overflowBottom = $( prefix + "x" + suffixBottom );
- } else {
- self._overflowTop = $( prefix + "y" + suffixTop );
- self._overflowBottom = $( prefix + "y" + suffixBottom );
- }
+Generally, web applications must be designed to be showed acceptable on various size and resolution of screens, and web winsets have to be scaled well. Tizen Web UI Framework supports various viewport settings, and Tizen Web UI widgets are designed to be scalable on various screen sizes. In order to make web applications scalable on many devices which have different screen size, it is necessary to understand how mobile web browsers deal with screen resolution, and how Tizen Web UI Framework supports scaling for web applications.
- self._$clip.append( self._overflowTop );
- self._$clip.append( self._overflowBottom );
- self._overflowDisplayed = false;
- },
- _hideVGOverflowIndicator : function () {
- if ( this._overflowDisplayed === false ) {
- return;
- }
+* Viewport on mobile web browser
- this._overflowTop.animate( { opacity: 0 }, 300 );
- this._overflowBottom.animate( { opacity: 0 }, 300 );
- this._overflowDisplayed = false;
- },
+Viewport is an area showing web content on the browser. Unlike desktop browsers, mobile browsers support logical viewport seting, which means that application can set viewport width/height and zoom level by itself.
+The very important thing that to be remembered is that the viewport resolution in pixel is 'Logical', not physical. For example, if the viewport width is set to 480 on a mobile device having 720px screen width, the viewport width is considered to 480px logically. All elements put on right side from 480px horizontal position will not be shown on the viewport.
+Most mobile browsers set viewport with given content attribute with <meta name="viewport" content="..."> tag in <head> section in the application source html, whereas desktop browsers ignore the tag.
+Detailed usage of viewport meta tag is found in here: http://www.w3.org/TR/mwabp/#bp-viewport
- //----------------------------------------------------//
- // Scrollbar //
- //----------------------------------------------------//
- _createScrollBar : function () {
- var self = this,
- prefix = "<div class=\"ui-scrollbar ui-scrollbar-",
- suffix = "\"><div class=\"ui-scrollbar-track\"><div class=\"ui-scrollbar-thumb\"></div></div></div>";
- if ( self.options.rotation ) {
- return ;
- }
+* Viewport setting by application developers
- if ( self._direction ) {
- self._$clip.append( prefix + "x" + suffix );
- self._hScrollBar = self._$clip.children( ".ui-scrollbar-x" );
- self._hScrollBar.find( ".ui-scrollbar-thumb" ).addClass( "ui-scrollbar-thumb-x" );
- } else {
- self._$clip.append( prefix + "y" + suffix );
- self._vScrollBar = self._$clip.children( ".ui-scrollbar-y" );
- self._vScrollBar.find( ".ui-scrollbar-thumb" ).addClass( "ui-scrollbar-thumb-y" );
- }
- },
+When developers write <meta name="viewport" content="..."> in the <head> section of the web application HTML file, Tizen Web UI Framework does not add another viewport meta tag, nor modify developer-defined viewport.
- _setScrollBarSize: function () {
- var self = this,
- scrollBarSize = 0,
- currentSize = 0,
- $scrollBar,
- attrName,
- className;
- if ( self.options.rotation ) {
- return ;
- }
+* Automatic viewport setting by Tizen Web UI Framework
- scrollBarSize = parseInt( self._maxViewSize / self._clipSize, 10 );
- if ( self._direction ) {
- $scrollBar = self._hScrollBar.find( ".ui-scrollbar-thumb" );
- attrName = "width";
- currentSize = $scrollBar.width();
- className = "ui-scrollbar-thumb-x";
- self._hScrollBar.css( "width", self._clipSize );
- } else {
- $scrollBar = self._vScrollBar.find( ".ui-scrollbar-thumb" );
- attrName = "height";
- className = "ui-scrollbar-thumb-y";
- currentSize = $scrollBar.height();
- self._vScrollBar.css( "height", self._clipSize );
- }
+If developers do not give a viewport meta tag, Tizen Web UI Framework automatically add a viewport meta tag with default viewport setting.
- if ( scrollBarSize > currentSize ) {
- $scrollBar.removeClass( className );
- $scrollBar.css( attrName, scrollBarSize );
- } else {
- scrollBarSize = currentSize;
- }
- self._itemScrollSize = parseFloat( ( self._clipSize - scrollBarSize ) / ( self._totalRowCnt - self._rowsPerView ) );
- self._itemScrollSize = Math.round( self._itemScrollSize * 100 ) / 100;
- },
+* Portrait/landscape mode
- _setScrollBarPosition : function ( di, duration ) {
- var self = this,
- $sbt = null,
- x = "0px",
- y = "0px",
- translate;
- if ( self.options.rotation ) {
- return ;
- }
+* Tizen Web UI widgets scaling
- self._currentItemCount = self._currentItemCount + di;
- if ( self._vScrollBar ) {
- $sbt = self._vScrollBar.find( ".ui-scrollbar-thumb" );
- y = ( self._currentItemCount * self._itemScrollSize ) + "px";
- } else {
- $sbt = self._hScrollBar.find( ".ui-scrollbar-thumb" );
- x = ( self._currentItemCount * self._itemScrollSize ) + "px";
- }
- self._setStyleTransform( $sbt, x, y, duration );
- },
- _hideScrollBars : function () {
- var self = this,
- vclass = "ui-scrollbar-visible";
+ */
+( function ($, Globalize, window, undefined) {
- if ( self.options.rotation ) {
- return ;
- }
+ var tizen = {
+ libFileName : "tizen-web-ui-fw(.min)?.js",
- if ( self._vScrollBar ) {
- self._vScrollBar.removeClass( vclass );
- } else {
- self._hScrollBar.removeClass( vclass );
- }
- },
+ frameworkData : {
+ rootDir: '/usr/lib/tizen-web-ui-fw',
+ version: '0.1',
+ theme: "tizen-white",
+ viewportWidth: "device-width",
+ viewportScale: false,
- _showScrollBars : function () {
- var self = this,
- vclass = "ui-scrollbar-visible";
+ defaultFontSize: 22,
+ minified: false,
- if ( self.options.rotation ) {
- return ;
- }
+ debug: false
+ },
- if ( self._vScrollBar ) {
- self._vScrollBar.addClass( vclass );
- } else {
- self._hScrollBar.addClass( vclass );
+ log : {
+ debug : function ( msg ) {
+ if ( tizen.frameworkData.debug ) {
+ console.log( msg );
+ }
+ },
+ warn : function ( msg ) {
+ console.warn( msg );
+ },
+ error : function ( msg ) {
+ console.error( msg );
+ },
+ alert : function ( msg ) {
+ window.alert( msg );
}
},
- //----------------------------------------------------//
- // scroll process //
- //----------------------------------------------------//
- centerTo : function ( selector ) {
- var self = this,
- row = null,
- targetItem = null,
- targetRowIndex = -1,
- rowsLength = self._$rows.length,
- newPosition,
- i;
+ util : {
- if ( !self.options.rotation ) {
- return;
+ loadScriptSync : function ( scriptPath, successCB, errorCB ) {
+ $.ajax( {
+ url: scriptPath,
+ dataType: 'script',
+ async: false,
+ crossDomain: false,
+ success: successCB,
+ error: function ( jqXHR, textStatus, errorThrown ) {
+ if ( errorCB ) {
+ errorCB( jqXHR, textStatus, errorThrown );
+ } else {
+ var ignoreStatusList = [ 404 ], // 404: not found
+ errmsg = ( 'Error while loading ' + scriptPath + '\n' + jqXHR.status + ':' + jqXHR.statusText );
+ if ( -1 == $.inArray( jqXHR.status, ignoreStatusList ) ) {
+ tizen.log.alert( errmsg );
+ } else {
+ tizen.log.warn( errmsg );
+ }
+ }
+ }
+ } );
+ },
+ isMobileBrowser: function ( ) {
+ var mobileIdx = window.navigator.appVersion.indexOf("Mobile"),
+ isMobile = -1 < mobileIdx;
+ return isMobile;
}
+ },
- for ( i = 0; i < rowsLength; ++i ) {
- row = $( self._$rows[ i ] );
- targetItem = row.children( "." + selector );
- if ( targetItem.length ) {
- targetRowIndex = parseInt( row.attr( "row-index" ), 10 );
- break;
+ css : {
+ cacheBust: ( document.location.href.match( /debug=true/ ) ) ?
+ '?cacheBust=' + ( new Date( ) ).getTime( ) :
+ '',
+ addElementToHead : function ( elem ) {
+ var head = document.getElementsByTagName( 'head' )[0];
+ if ( head ) {
+ $( head ).prepend( elem );
}
- }
-
- if ( targetRowIndex === -1 ) {
- targetRowIndex = self._getTargetRowIndex( selector );
- if ( targetRowIndex === -1 ) {
- return;
+ },
+ makeLink : function ( href ) {
+ var cssLink = document.createElement( 'link' );
+ cssLink.setAttribute( 'rel', 'stylesheet' );
+ cssLink.setAttribute( 'href', href );
+ cssLink.setAttribute( 'name', 'tizen-theme' );
+ return cssLink;
+ },
+ load: function ( path ) {
+ var head = document.getElementsByTagName( 'head' )[0],
+ cssLinks = head.getElementsByTagName( 'link' ),
+ idx,
+ l = null;
+ // Find css link element
+ for ( idx = 0; idx < cssLinks.length; idx++ ) {
+ if ( cssLinks[idx].getAttribute( 'rel' ) != "stylesheet" ) {
+ continue;
+ }
+ if ( cssLinks[idx].getAttribute( 'name' ) == "tizen-theme"
+ || cssLinks[idx].getAttribute( 'href' ) == path ) {
+ l = cssLinks[idx];
+ break;
+ }
+ }
+ if ( l ) { // Found the link element!
+ if ( l.getAttribute( 'href' ) == path ) {
+ tizen.log.warn( "Theme is already loaded. Skip theme loading in the framework." );
+ } else {
+ l.setAttribute( 'href', path );
+ }
+ } else {
+ this.addElementToHead( this.makeLink( path ) );
}
- }
-
- newPosition = -( targetRowIndex * self._cellSize - ( self._clipSize - self._cellSize ) / 2 );
- if ( self._direction ) {
- self.scrollTo( newPosition, 0 );
- } else {
- self.scrollTo( 0, newPosition );
}
},
- _getTargetRowIndex: function ( selector ) {
- var self = this,
- dataCount = self._numItemData,
- itemCount = self._itemCount,
- attrName = self._direction ? "top" : "left",
- html = "",
- targetRowIndex = self._totalRowCnt,
- i;
+ getParams: function ( ) {
+ /* Get data-* params from <script> tag, and set tizen.frameworkData.* values
+ * Returns true if proper <script> tag is found, or false if not.
+ */
+ // Find current <script> tag element
+ var scriptElems = document.getElementsByTagName( 'script' ),
+ val = null,
+ foundScriptTag = false,
+ idx,
+ elem,
+ src,
+ tokens,
+ version_idx;
- for ( i = 0; i < dataCount; ++i ) {
- html = self._makeHtmlData( i, i % itemCount, attrName );
- if ( self._hasClassItem( html, selector ) ) {
- targetRowIndex = parseInt( i / itemCount, 10 );
- break;
+ function getTizenTheme( ) {
+ var t = navigator.theme ? navigator.theme.split( ':' )[0] : null;
+ if ( t ) {
+ t = t.replace('-hd', '');
+ if ( ! t.match( /^tizen-/ ) ) {
+ t = 'tizen-' + t;
+ }
}
+ return t;
}
- if ( targetRowIndex === self._totalRowCnt ) {
- return -1;
+ for ( idx in scriptElems ) {
+ elem = scriptElems[idx];
+ src = elem.src ? elem.getAttribute( 'src' ) : undefined;
+ if (src && src.match( this.libFileName )) {
+ // Set framework data, only when they are given.
+ tokens = src.split(/[\/\\]/);
+ version_idx = -3;
+ this.frameworkData.rootDir = ( elem.getAttribute( 'data-framework-root' )
+ || tokens.slice( 0, tokens.length + version_idx ).join( '/' )
+ || this.frameworkData.rootDir ).replace( /^file:(\/\/)?/, '' );
+ this.frameworkData.version = elem.getAttribute( 'data-framework-version' )
+ || tokens[ tokens.length + version_idx ]
+ || this.frameworkData.version;
+ this.frameworkData.theme = elem.getAttribute( 'data-framework-theme' )
+ || getTizenTheme( )
+ || this.frameworkData.theme;
+ this.frameworkData.viewportWidth = elem.getAttribute( 'data-framework-viewport-width' )
+ || this.frameworkData.viewportWidth;
+ this.frameworkData.viewportScale =
+ "true" === elem.getAttribute( 'data-framework-viewport-scale' ) ? true
+ : this.frameworkData.viewportScale;
+ this.frameworkData.minified = src.search(/\.min\.js$/) > -1 ? true : false;
+ this.frameworkData.debug = "true" === elem.getAttribute( 'data-framework-debug' ) ? true
+ : this.frameworkData.debug;
+ foundScriptTag = true;
+ break;
+ }
}
-
- return targetRowIndex;
+ return foundScriptTag;
},
- _hasClassItem: function ( html, selector ) {
- var self = this,
- classString = self._getItemClass( html );
-
- if ( classString.indexOf( selector ) === -1 ) {
- return false;
- }
+ loadTheme: function ( theme ) {
+ var themePath,
+ cssPath,
+ jsPath;
- if ( classString.indexOf( "virtualgrid-item" ) === -1 ) {
- return false;
+ if ( ! theme ) {
+ theme = tizen.frameworkData.theme;
}
-
- return true;
- },
-
- _getItemClass: function ( html ) {
- var classIndex = html.indexOf( "class" ),
- classBeginIndex = Math.min( html.indexOf( "\"", classIndex ), html.indexOf( "'", classIndex ) ),
- classEndIndex = Math.min( html.indexOf( "\"", classBeginIndex + 1 ), html.indexOf( "'", classBeginIndex + 1 ) );
-
- return html.slice( classBeginIndex + 1, classEndIndex );
- },
-
- scrollTo: function ( x, y, duration ) {
- var self = this;
- if ( self._direction ) {
- x -= self._cellSize;
- self._sx = self._reservedPos;
- self._reservedPos = x;
+
+ themePath = tizen.frameworkData.rootDir + '/' + tizen.frameworkData.version + '/themes/' + theme;
+
+ jsPath = themePath + '/theme.js';
+
+ if ( tizen.frameworkData.minified ) {
+ cssPath = themePath + '/tizen-web-ui-fw-theme.min.css';
} else {
- y -= self._cellSize;
- self._sy = self._reservedPos;
- self._reservedPos = y;
- }
- self._scrollView.scrollTo.apply( this, [ x, y, duration ] );
- },
-
- getScrollPosition: function () {
- if ( this.direction ) {
- return { x: -this._ry, y: 0 };
+ cssPath = themePath + '/tizen-web-ui-fw-theme.css';
}
- return { x: 0, y: -this._ry };
+ tizen.css.load( cssPath );
+ tizen.util.loadScriptSync( jsPath );
},
- _setScrollPosition: function ( x, y ) {
+ /** Load Globalize culture file, and set default culture.
+ * @param[in] language (optional) Language code. ex) en-US, en, ko-KR, ko
+ * If language is not given, read language from html 'lang' attribute,
+ * or from system setting.
+ * @param[in] cultureDic (optional) Dictionary having language code->
+ */
+ loadGlobalizeCulture: function ( language, cultureDic ) {
var self = this,
- sy = self._scalableSize,
- distance = self._direction ? x : y,
- dy = distance - sy,
- di = parseInt( dy / self._cellSize, 10 ),
- i = 0,
- idx = 0,
- replaceStartIdx = 0,
- realRowCount = self._rowsPerView + 2,
- rawView = self._$view[0];
-
- if ( self._blockScroll ) {
- if ( dy > 0 && distance >= -self._cellSize && self._scalableSize >= -self._cellSize ) {
- self._overflowDir = _OVERFLOW_DIR_UP;
- }
- if ( dy < 0 && self._scalableSize <= -( self._maxSizeExceptClip + self._cellSize ) ) {
- self._overflowDir = _OVERFLOW_DIR_DOWN;
- }
- return;
- }
+ cFPath,
+ lang,
+ mockJSXHR;
- if ( ! self.options.rotation ) {
- if ( dy > 0 && distance >= -self._cellSize && self._scalableSize >= -self._cellSize ) {
- // top
- self._stopMScroll();
- self._scalableSize = -self._cellSize;
- self._setElementTransform( -self._cellSize );
- if ( self._overflowDir === _OVERFLOW_DIR_NONE ) {
- self._overflowDir = _OVERFLOW_DIR_UP;
- }
- return;
- }
- if ( dy < 0 && self._scalableSize <= -( self._maxSizeExceptClip + self._cellSize ) ) {
- // bottom
- self._stopMScroll();
- self._scalableSize = -( self._maxSizeExceptClip + self._cellSize );
- self._setElementTransform( self._modifyViewPos );
- if ( self._overflowDir === _OVERFLOW_DIR_NONE ) {
- self._overflowDir = _OVERFLOW_DIR_DOWN;
+ function getLang ( language ) {
+ var lang = language
+ || $( 'html' ).attr( 'lang' )
+ || window.navigator.language.split( '.' )[0] // Webkit, Safari + workaround for Tizen
+ || window.navigator.userLanguage // IE
+ || 'en',
+ countryCode = null,
+ countryCodeIdx = lang.lastIndexOf('-'),
+ ignoreCodes = ['Cyrl', 'Latn', 'Mong']; // Not country code!
+ if ( countryCodeIdx != -1 ) { // Found country code!
+ countryCode = lang.substr( countryCodeIdx + 1 );
+ if ( ignoreCodes.join( '-' ).indexOf( countryCode ) < 0 ) {
+ // countryCode is not found from ignoreCodes.
+ // Make countryCode to uppercase.
+ lang = [ lang.substr( 0, countryCodeIdx ), countryCode.toUpperCase( ) ].join( '-' );
}
- return;
}
+ // NOTE: 'en' to 'en-US', because globalize has no 'en' culture file.
+ lang = lang == 'en' ? 'en-US' : lang;
+ return lang;
}
- replaceStartIdx = ( Math.abs( di ) < realRowCount ) ? 0 : ( di > 0 ) ? di - realRowCount : di + realRowCount;
- if ( di > 0 ) { // scroll up
- for ( i = replaceStartIdx; i < di; ++i ) {
- idx = -parseInt( ( sy / self._cellSize ) + i + 3, 10 );
- self._replaceRow( rawView.lastChild, circularNum( idx, self._totalRowCnt ) );
- rawView.insertBefore( rawView.lastChild, rawView.firstChild );
- }
- } else if ( di < 0 ) { // scroll down
- for ( i = replaceStartIdx; i > di; --i ) {
- idx = self._rowsPerView - parseInt( ( sy / self._cellSize ) + i, 10 );
- self._replaceRow( rawView.firstChild, circularNum( idx, self._totalRowCnt ) );
- rawView.insertBefore( rawView.firstChild, rawView.lastChild.nextSibling );
+ function getNeutralLang ( lang ) {
+ var neutralLangIdx = lang.lastIndexOf( '-' ),
+ neutralLang;
+ if ( neutralLangIdx != -1 ) {
+ neutralLang = lang.substr( 0, neutralLangIdx );
}
+ return neutralLang;
}
- self._setScrollBarPosition( -di );
- self._scalableSize += di * self._cellSize;
- self._setElementTransform( distance - self._scalableSize - self._cellSize );
- },
-
- _setElementTransform : function ( value ) {
- var self = this,
- x = 0,
- y = 0;
-
- if ( self._direction ) {
- x = value + "px";
- } else {
- y = value + "px";
- }
- self._setStyleTransform( self._$view, x, y );
- },
- //----------------------------------------------------//
- // Event handler //
- //----------------------------------------------------//
- _handleMomentumScroll: function () {
- var self = this,
- opts = self.options,
- keepGoing = false,
- v = this._$view,
- x = 0,
- y = 0,
- t = self._tracker;
+ function getCultureFilePath ( lang, cFDic ) {
+ var cFPath = null; // error value
- if ( t ) {
- t.update();
- if ( self._direction ) {
- x = t.getPosition();
+ if ( "string" != typeof lang ) {
+ return null;
+ }
+ if ( cFDic && cFDic[lang] ) {
+ cFPath = cFDic[lang];
} else {
- y = t.getPosition();
+ // Default Globalize culture file path
+ cFPath = [
+ self.frameworkData.rootDir,
+ self.frameworkData.version,
+ 'js',
+ 'cultures',
+ ['globalize.culture.', lang, '.js'].join( '' )
+ ].join( '/' );
}
- keepGoing = !t.done();
+ return cFPath;
}
- self._setScrollPosition( x, y );
- if ( !opts.rotation ) {
- keepGoing = !t.done();
- self._reservedPos = self._direction ? x : y;
- // bottom
- self._reservedPos = self._reservedPos <= (-(self._maxSizeExceptClip - self._modifyViewPos)) ? ( - ( self._maxSizeExceptClip + self._cellSize) ) : self._reservedPos;
- // top
- self._reservedPos = self._reservedPos > -self._cellSize ? -self._cellSize : self._reservedPos;
- } else {
- self._reservedPos = self._direction ? x : y;
+ function printLoadError( cFPath, jqXHR ) {
+ tizen.log.error( "Error " + jqXHR.status + ": " + jqXHR.statusText
+ + "::Culture file (" + cFPath + ") is failed to load.");
}
- self._$clip.trigger( self.options.updateEventName, [ { x: x, y: y } ] );
- if ( keepGoing ) {
- self._timerID = setTimeout( self._timerCB, self._timerInterval );
- } else {
- self._stopMScroll();
- }
- },
+ function loadCultureFile ( cFPath, errCB ) {
+ function _successCB ( ) {
+ tizen.log.debug( "Culture file (" + cFPath + ") is loaded successfully." );
+ }
+ function _errCB ( jqXHR, textStatus, err ) {
+ if ( errCB ) {
+ errCB( jqXHR, textStatus, err );
+ } else {
+ printLoadError( cFPath, jqXHR );
+ }
+ }
- _startMScroll: function ( speedX, speedY ) {
- var self = this;
- if ( self._direction ) {
- self._sx = self._reservedPos;
- } else {
- self._sy = self._reservedPos;
+ if ( ! cFPath ) { // Invalid cFPath -> Regard it as '404 Not Found' error.
+ mockJSXHR = {
+ status: 404,
+ statusText: "Not Found"
+ };
+ _errCB( mockJSXHR, null, null );
+ } else {
+ $.ajax( {
+ url: cFPath,
+ dataType: 'script',
+ cache: true,
+ async: false,
+ success: _successCB,
+ error: _errCB
+ } );
+ }
}
- self._scrollView._startMScroll.apply( self, [ speedX, speedY ] );
- },
- _stopMScroll: function () {
- this._scrollView._stopMScroll.apply( this );
- },
+ lang = getLang( language );
+ cFPath = getCultureFilePath( lang, cultureDic );
+ loadCultureFile( cFPath,
+ function ( jqXHR, textStatus, err ) {
+ if ( jqXHR.status == 404 ) {
+ // If culture file is not found, try once more with neutral lang.
+ var nLang = getNeutralLang( lang ),
+ ncFPath = getCultureFilePath( nLang, cultureDic );
+ loadCultureFile( ncFPath, null );
+ } else {
+ printLoadError( cFPath, jqXHR );
+ }
+ } );
- _enableTracking: function () {
- var self = this;
- self._$view.bind( self._dragMoveEvt, self._dragMoveCB );
- self._$view.bind( self._dragStopEvt, self._dragStopCB );
- self._scrollView._enableTracking.apply( self );
+ return lang;
},
+ setGlobalize: function ( ) {
+ var lang = this.loadGlobalizeCulture( );
- _disableTracking: function () {
- var self = this;
- self._$view.unbind( self._dragMoveEvt, self._dragMoveCB );
- self._$view.unbind( self._dragStopEvt, self._dragStopCB );
- self._scrollView._disableTracking.apply( self );
+ // Set culture
+ // NOTE: It is not needed to set with neutral lang.
+ // Globalize automatically deals with it.
+ Globalize.culture( lang );
},
-
- _handleDragStart: function ( e, ex, ey ) {
- var self = this;
- self._scrollView._handleDragStart.apply( this, [ e, ex, ey ] );
- self._eventPos = self._direction ? ex : ey;
- self._nextPos = self._reservedPos;
+ /**
+ * Load custom globalize culture file
+ * Find current system language, and load appropriate culture file from given colture file list.
+ *
+ * @param[in] cultureDic collection of 'language':'culture file path' key-val pair.
+ * @example
+ * var myCultures = {
+ * "en" : "culture/en.js",
+ * "fr" : "culture/fr.js",
+ * "ko-KR" : "culture/ko-KR.js"
+ * };
+ * loadCultomGlobalizeCulture( myCultures );
+ *
+ * ex) culture/fr.js
+ * -------------------------------
+ * Globalize.addCultureInfo( "fr", {
+ * messages: {
+ * "hello" : "bonjour",
+ * "translate" : "traduire"
+ * }
+ * } );
+ * -------------------------------
+ */
+ loadCustomGlobalizeCulture: function ( cultureDic ) {
+ tizen.loadGlobalizeCulture( null, cultureDic );
},
- _handleDragMove: function ( e, ex, ey ) {
- var self = this,
- dx = ex - self._lastX,
- dy = ey - self._lastY,
- x = 0,
- y = 0,
- diffFromStartPos = 0,
- diffFromLastPos = 0,
- opacity = 0,
- overflowPos = 0,
- overFlowTarget = null;
-
- self._lastMove = getCurrentTime();
- self._speedX = dx;
- self._speedY = dy;
-
- self._didDrag = true;
-
- self._lastX = ex;
- self._lastY = ey;
+ /** Set viewport meta tag for mobile devices.
+ *
+ * @param[in] viewportWidth viewport width. "device-width" is OK.
+ */
+ setViewport: function ( viewportWidth ) {
+ var meta = null,
+ head,
+ content;
- if ( self._direction ) {
- self._movePos = ex - self._eventPos;
- x = self._nextPos + self._movePos;
- overflowPos = ex;
+ // Do nothing if viewport setting code is already in the code.
+ $( "meta[name=viewport]" ).each( function ( ) {
+ meta = this;
+ return;
+ });
+ if ( meta ) { // Found custom viewport!
+ content = $( meta ).prop( "content" );
+ viewportWidth = content.replace( /.*width=(device-width|\d+)\s*,?.*$/gi, "$1" );
+ tizen.log.warn( "Viewport is set to '" + viewportWidth + "' in a meta tag. Framework skips viewport setting." );
} else {
- self._movePos = ey - self._eventPos;
- y = self._nextPos + self._movePos;
- overflowPos = ey;
- }
- self._showScrollBars();
- self._setScrollPosition( x, y );
- if ( self._overflowDir !== _OVERFLOW_DIR_NONE ) {
- overFlowTarget = ( self._overflowDir === _OVERFLOW_DIR_UP ) ? self._overflowTop : self._overflowBottom;
- if ( !self._overflowDisplayed ) {
- self._overflowDisplayed = true;
- self._overflowStartPos = overflowPos;
+ // Create a meta tag
+ meta = document.createElement( "meta" );
+ if ( meta ) {
+ meta.name = "viewport";
+ content = "width=" + viewportWidth + ", user-scalable=no";
+ if ( ! isNaN( viewportWidth ) ) {
+ // Fix scale to 1.0, if viewport width is set to fixed value.
+ // NOTE: Works wrong in Tizen browser!
+ //content = [ content, ", initial-scale=1.0, maximum-scale=1.0" ].join( "" );
+ }
+ meta.content = content;
+ tizen.log.debug( content );
+ head = document.getElementsByTagName( 'head' ).item( 0 );
+ head.insertBefore( meta, head.firstChild );
}
- diffFromStartPos = ( overflowPos - self._overflowStartPos ) * self._overflowDir;
- opacity = ( diffFromStartPos < 0 ) ?
- 0 : ( diffFromStartPos > self._overflowMaxDragDist ) ?
- 1 : ( diffFromStartPos / self._overflowMaxDragDist );
- overFlowTarget.css( "opacity", opacity );
}
+ return viewportWidth;
+ },
- return false;
+ /** Read body's font-size, scale it, and reset it.
+ * param[in] desired font-size / base font-size.
+ */
+ scaleBaseFontSize: function ( themeDefaultFontSize, ratio ) {
+ tizen.log.debug( "themedefaultfont size: " + themeDefaultFontSize + ", ratio: " + ratio );
+ var scaledFontSize = Math.max( Math.floor( themeDefaultFontSize * ratio ), 4 );
+
+ $( 'html' ).css( { 'font-size': scaledFontSize + "px" } );
+ tizen.log.debug( 'html:font size is set to ' + scaledFontSize );
+ $( document ).ready( function ( ) {
+ $( '.ui-mobile' ).children( 'body' ).css( { 'font-size': scaledFontSize + "px" } );
+ } );
},
- _handleDragStop: function ( e ) {
- var self = this;
+ setScaling: function ( ) {
+ var viewportWidth = this.frameworkData.viewportWidth,
+ themeDefaultFontSize = this.frameworkData.defaultFontSize, // comes from theme.js
+ ratio = 1;
- self._reservedPos = self._movePos ? self._nextPos + self._movePos : self._reservedPos;
- self._scrollView._handleDragStop.apply( this, [ e ] );
- if ( self._overflowDir !== _OVERFLOW_DIR_NONE ) {
- self._overflowDir = _OVERFLOW_DIR_NONE;
- self._hideVGOverflowIndicator();
+ // Keep original font size
+ $( 'body' ).attr( 'data-tizen-theme-default-font-size', themeDefaultFontSize );
+
+ if ( !tizen.util.isMobileBrowser() ) {
+ return;
}
- return self._didDrag ? false : undefined;
- },
- _addBehaviors: function () {
- var self = this;
+ // Legacy support: tizen.frameworkData.viewportScale
+ if ( this.frameworkData.viewportScale == true ) {
+ viewportWidth = "screen-width";
+ }
- // scroll event handler.
- if ( self.options.eventType === "mouse" ) {
- self._dragStartEvt = "mousedown";
- self._dragStartCB = function ( e ) {
- return self._handleDragStart( e, e.clientX, e.clientY );
- };
+ // screen-width support
+ if ( "screen-width" == viewportWidth ) {
+ if ( window.self == window.top ) {
+ // Top frame: for target. Use window.outerWidth.
+ viewportWidth = window.outerWidth;
+ } else {
+ // iframe: for web simulator. Use clientWidth.
+ viewportWidth = document.documentElement.clientWidth;
+ }
+ }
- self._dragMoveEvt = "mousemove";
- self._dragMoveCB = function ( e ) {
- return self._handleDragMove( e, e.clientX, e.clientY );
- };
+ // set viewport meta tag
+ viewportWidth = this.setViewport( viewportWidth ); // If custom viewport setting exists, get viewport width
- self._dragStopEvt = "mouseup";
- self._dragStopCB = function ( e ) {
- return self._handleDragStop( e, e.clientX, e.clientY );
- };
+ if ( viewportWidth == "device-width" ) {
+ // Do nothing!
+ } else { // fixed width!
+ ratio = parseFloat( viewportWidth / this.frameworkData.defaultViewportWidth );
+ this.scaleBaseFontSize( themeDefaultFontSize, ratio );
+ }
+ }
+ };
- self._$view.bind( "vclick", function ( e ) {
- return !self._didDrag;
- } );
- } else { //touch
- self._dragStartEvt = "touchstart";
- self._dragStartCB = function ( e ) {
- var t = e.originalEvent.targetTouches[0];
- return self._handleDragStart( e, t.pageX, t.pageY );
- };
+ function export2TizenNS ( $, tizen ) {
+ if ( !$.tizen ) {
+ $.tizen = { };
+ }
- self._dragMoveEvt = "touchmove";
- self._dragMoveCB = function ( e ) {
- var t = e.originalEvent.targetTouches[0];
- return self._handleDragMove( e, t.pageX, t.pageY );
- };
+ $.tizen.frameworkData = tizen.frameworkData;
+ $.tizen.loadCustomGlobalizeCulture = tizen.loadCustomGlobalizeCulture;
+ $.tizen.loadTheme = tizen.loadTheme;
- self._dragStopEvt = "touchend";
- self._dragStopCB = function ( e ) {
- return self._handleDragStop( e );
- };
- }
- self._$view.bind( self._dragStartEvt, self._dragStartCB );
+ $.tizen.__tizen__ = tizen; // for unit-test
+ }
- // other events.
- self._$view.delegate( ".virtualgrid-item", "click", function ( event ) {
- var $selectedItem = $( this );
- $selectedItem.trigger( "select", this );
- } );
+ export2TizenNS( $, tizen );
- $( window ).bind( "resize", function ( e ) {
- var height = 0,
- $virtualgrid = $( ".ui-virtualgrid-view" );
- if ( $virtualgrid.length !== 0 ) {
- self._resize();
- }
- } );
+ tizen.getParams( );
+ tizen.loadTheme( );
+ tizen.setScaling( ); // Run after loadTheme(), for the default font size.
+ tizen.setGlobalize( );
+ // Turn off JQM's auto initialization option.
+ // NOTE: This job must be done before domready.
+ $.mobile.autoInitializePage = false;
- $( document ).one( "pageshow", function ( event ) {
- var $page = $( self.element ).parents( ".ui-page" ),
- $header = $page.find( ":jqmData(role='header')" ),
- $footer = $page.find( ":jqmData(role='footer')" ),
- $content = $page.find( ":jqmData(role='content')" ),
- footerHeight = $footer ? $footer.height() : 0,
- headerHeight = $header ? $header.height() : 0;
+ $(document).ready( function ( ) {
+ $.mobile.initializePage( );
+ });
- if ( $page && $content ) {
- $content.height( window.innerHeight - headerHeight - footerHeight ).css( "overflow", "hidden" );
- $content.addClass( "ui-virtualgrid-content" );
- }
- } );
- },
+} ( jQuery, window.Globalize, window ) );
- //----------------------------------------------------//
- // Calculate size about dom element. //
- //----------------------------------------------------//
- _calculateClipSize : function () {
- var self = this,
- clipSize = 0;
- if ( self._direction ) {
- clipSize = self._calculateClipWidth();
- } else {
- clipSize = self._calculateClipHeight();
- }
- return clipSize;
- },
- _calculateClipWidth : function () {
- var self = this,
- $parent = self._$clip.parent(),
- paddingValue = 0,
- clipSize = $( window ).width();
+/*
+ * jQuery UI Progressbar @VERSION
+ *
+ * Copyright 2011, AUTHORS.txt (http://jqueryui.com/about)
+ * Dual licensed under the MIT or GPL Version 2 licenses.
+ * http://jquery.org/license
+ *
+ * http://docs.jquery.com/UI/Progressbar
+ *
+ * Depends:
+ * jquery.ui.core.js
+ * jquery.ui.widget.js
+ * Original file:
+ * jquery.ui.progressbar.js
+ */
+/* This is from jquery ui plugin - progressbar 11/16/2011 */
- if ( self._inheritedSize.isDefinedWidth ) {
- return self._inheritedSize.width;
- }
- if ( $parent.hasClass( "ui-content" ) ) {
- paddingValue = parseInt( $parent.css( "padding-left" ), 10 );
- clipSize = clipSize - ( paddingValue || 0 );
- paddingValue = parseInt( $parent.css( "padding-right" ), 10 );
- clipSize = clipSize - ( paddingValue || 0 );
- } else {
- clipSize = self._$clip.width();
- }
- return clipSize;
- },
+/**
+ @class ProgressBar
+ The progress bar widget shows a control that indicates the progress percentage of an on-going operation. This widget can be scaled to fit inside a parent container.
- _calculateClipHeight : function () {
- var self = this,
- $parent = self._$clip.parent(),
- header = null,
- footer = null,
- paddingValue = 0,
- clipSize = $( window ).height();
+ To add a progress bar widget to the application, use the following code:
- if ( self._inheritedSize.isDefinedHeight ) {
- return self._inheritedSize.height;
- }
+ <div id="foo" data-role="progressbar"</div>
+*/
+/**
+ @event change
+ The progress bar can define a callback for the change event, which is fired when the progress value is changed:
+ <div id="foo" data-role="progressbar"></div>
+ $("#foo").bind("change", function (ev, val) {
+ Console.log("Value is changed to " + val);
+ });
+*/
+/**
+ @method value
+ You can use the value method with the pickers to set or get the current default progress bar value:
- if ( $parent.hasClass( "ui-content" ) ) {
- paddingValue = parseInt( $parent.css( "padding-top" ), 10 );
- clipSize = clipSize - ( paddingValue || 0 );
- paddingValue = parseInt( $parent.css( "padding-bottom" ), 10 );
- clipSize = clipSize - ( paddingValue || 0 );
- header = $parent.siblings( ".ui-header" );
- footer = $parent.siblings( ".ui-footer" );
+ <div id="foo" data-role="progressbar"></div>
+ var oldVal = $("#foo").progressbar("value");
+ $("#foo").progressbar("value", 50);
+*/
- if ( header ) {
- if ( header.outerHeight( true ) === null ) {
- clipSize = clipSize - ( $( ".ui-header" ).outerHeight() || 0 );
- } else {
- clipSize = clipSize - header.outerHeight( true );
- }
- }
- if ( footer ) {
- clipSize = clipSize - footer.outerHeight( true );
- }
- } else {
- clipSize = self._$clip.height();
- }
- return clipSize;
+(function ( $, window, undefined ) {
+
+ $.widget( "tizen.progressbar", $.mobile.widget, {
+ options: {
+ value: 0,
+ max: 100
},
- _calculateColumnSize : function () {
- var self = this,
- $tempBlock,
- $cell;
+ min: 0,
- $tempBlock = $( self._makeRows( 1 ) );
- self._$view.append( $tempBlock.children().first() );
- if ( self._direction ) {
- // x-axis
- self._viewSize = self._$view.width();
- $cell = self._$view.children().first().children().first();
- self._cellSize = $cell.outerWidth( true );
- self._cellOtherSize = $cell.outerHeight( true );
- } else {
- // y-axis
- self._viewSize = self._$view.height();
- $cell = self._$view.children().first().children().first();
- self._cellSize = $cell.outerHeight( true );
- self._cellOtherSize = $cell.outerWidth( true );
- }
- $tempBlock.remove();
- self._$view.children().remove();
- },
+ _create: function () {
+ this.element
+ .addClass( "ui-progressbar" )
+ .attr( {
+ role: "progressbar",
+ "aria-valuemin": this.min,
+ "aria-valuemax": this.options.max,
+ "aria-valuenow": this._value()
+ } );
- _calculateColumnCount : function ( ) {
- var self = this,
- $view = self._$clip,
- viewSize = self._direction ? $view.innerHeight() : $view.innerWidth(),
- itemCount = 0 ;
+ this.valueDiv = $( "<div class='ui-progressbar-value'></div>" )
+ .appendTo( this.element );
- if ( self._direction ) {
- viewSize = viewSize - ( parseInt( $view.css( "padding-top" ), 10 ) + parseInt( $view.css( "padding-bottom" ), 10 ) );
- } else {
- viewSize = viewSize - ( parseInt( $view.css( "padding-left" ), 10 ) + parseInt( $view.css( "padding-right" ), 10 ) );
- }
+ this.valueDiv.wrap("<div class='ui-progressbar-bg'></div>");
- itemCount = parseInt( ( viewSize / self._cellOtherSize ), 10 );
- return itemCount > 0 ? itemCount : 1 ;
+ this.oldValue = this._value();
+ this._refreshValue();
},
- // Read the position of clip form property ('webkit-transform').
- // @return : number - position of clip.
- _getClipPosition : function () {
- var self = this,
- matrix = null,
- contents = null,
- result = -self._cellSize,
- $scrollview = self._$view.closest( ".ui-scrollview-view" );
-
- if ( $scrollview ) {
- matrix = $scrollview.css( "-webkit-transform" );
- contents = matrix.substr( 7 );
- contents = contents.substr( 0, contents.length - 1 );
- contents = contents.split( ', ' );
- result = Math.abs( contents [5] );
- }
- return result;
+ _destroy: function () {
+ this.element
+ .removeClass( "ui-progressbar" )
+ .removeAttr( "role" )
+ .removeAttr( "aria-valuemin" )
+ .removeAttr( "aria-valuemax" )
+ .removeAttr( "aria-valuenow" );
+
+ this.valueDiv.remove();
},
- //----------------------------------------------------//
- // DOM Element handle //
- //----------------------------------------------------//
- _makeRows : function ( count ) {
- var self = this,
- index = 0,
- row = null,
- wrapper = null;
+ value: function ( newValue ) {
+ if ( newValue === undefined ) {
+ return this._value();
+ }
- wrapper = self._createElement( "div" );
- wrapper.setAttribute( "class", "ui-scrollview-view" );
- for ( index = 0; index < count ; index += 1 ) {
- row = self._makeRow( index );
- if ( self._direction ) {
- row.style.top = 0;
- row.style.left = index * self._cellSize;
+ this._setOption( "value", newValue );
+ return this;
+ },
+
+ _setOption: function ( key, value ) {
+ if ( key === "value" ) {
+ this.options.value = value;
+ this._refreshValue();
+ if ( this._value() === this.options.max ) {
+ this.element.trigger( "complete" );
}
- wrapper.appendChild( row );
}
- return wrapper;
+ // jquery.ui.widget.js MUST be updated to new version!
+ //this._super( "_setOption", key, value );
},
- // make a single row block
- _makeRow : function ( rowIndex ) {
- var self = this,
- index = rowIndex * self._itemCount,
- colIndex = 0,
- blockClassName = self._direction ? "ui-virtualgrid-wrapblock-x" : "ui-virtualgrid-wrapblock-y",
- wrapBlock = self._createElement( "div" ),
- strWrapInner = "",
- attrName = self._direction ? "top" : "left";
-
- for ( colIndex = 0; colIndex < self._itemCount; colIndex++ ) {
- strWrapInner += self._makeHtmlData( index, colIndex, attrName );
- index += 1;
+ _value: function () {
+ var val = this.options.value;
+ // normalize invalid value
+ if ( typeof val !== "number" ) {
+ val = 0;
}
- wrapBlock.innerHTML = strWrapInner;
- wrapBlock.setAttribute( "class", blockClassName );
- wrapBlock.setAttribute( "row-index", String( rowIndex ) );
- self._fragment.appendChild( wrapBlock );
- return wrapBlock;
+ return Math.min( this.options.max, Math.max( this.min, val ) );
},
- _makeHtmlData : function ( dataIndex, colIndex, attrName ) {
- var self = this,
- htmlStr = "",
- itemData = null;
+ _percentage: function () {
+ return 100 * this._value() / this.options.max;
+ },
- itemData = self._itemData( dataIndex );
- if ( itemData ) {
- htmlStr = self._getConvertedTmplStr( itemData );
- htmlStr = self._insertPosToTmplStr( htmlStr, attrName, ( colIndex * self._cellOtherSize ) );
+ _refreshValue: function () {
+ var value = this.value(),
+ percentage = this._percentage();
+
+ if ( this.oldValue !== value ) {
+ this.oldValue = value;
+ this.element.trigger( "change" );
}
- return htmlStr;
- },
+ this.valueDiv
+ .toggle( value > this.min )
+ .width( percentage.toFixed(0) + "%" );
+ this.element.attr( "aria-valuenow", value );
+ }
+ } );
- _insertPosToTmplStr : function ( tmplStr, attrName, posVal ) {
- var tagCloseIdx = tmplStr.indexOf( '>' ),
- classIdx = -1,
- firstPart,
- lastPart,
- result,
- found = false,
- targetIdx = 0,
- firstPartLen,
- i = 0;
+ // auto self-init widgets
+ $( document ).bind( "pagecreate", function ( e ) {
+ $( e.target ).find( ":jqmData(role='progressbar')" ).progressbar();
+ } );
- if ( tagCloseIdx === -1 ) {
- return;
- }
+}( jQuery, this ) );
- firstPart = tmplStr.slice( 0, tagCloseIdx );
- lastPart = tmplStr.slice( tagCloseIdx, tmplStr.length );
- classIdx = firstPart.indexOf( 'class' );
- if ( classIdx !== -1 ) {
- firstPartLen = firstPart.length;
- for ( i = classIdx + 6; i < firstPartLen; i++ ) {
- if ( firstPart.charAt( i ) === "\"" || firstPart.charAt( i ) === "\'" ) {
- if ( found === false ) {
- found = true;
- } else {
- targetIdx = i;
- break;
- }
- }
- }
- result = firstPart.slice( 0, targetIdx ) + " virtualgrid-item" + firstPart.slice( targetIdx, firstPartLen ) + lastPart;
- } else {
- result = firstPart + " class=\"virtualgrid-item\"" + lastPart;
- }
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Author: Jinhyuk Jun <jinhyuk.jun@samsung.com>
+ */
- if ( !isNaN( posVal ) ) {
- result = result.replace( '>', " style=\"" + attrName + ": " + String( posVal ) + "px\">");
- }
+(function ( $, undefined ) {
- return result;
+ $.widget( "mobile.pagelayout", $.mobile.widget, {
+ options: {
+ visibleOnPageShow: true,
+ disablePageZoom: true,
+ transition: "slide", //can be none, fade, slide (slide maps to slideup or slidedown)
+ fullscreen: false,
+ tapToggle: true,
+ tapToggleBlacklist: "a, input, select, textarea, .ui-header-fixed, .ui-footer-fixed",
+ hideDuringFocus: "input, textarea, select",
+ updatePagePadding: true,
+ // Browser detection! Weeee, here we go...
+ // Unfortunately, position:fixed is costly, not to mention probably impossible, to feature-detect accurately.
+ // Some tests exist, but they currently return false results in critical devices and browsers, which could lead to a broken experience.
+ // Testing fixed positioning is also pretty obtrusive to page load, requiring injected elements and scrolling the window
+ // The following function serves to rule out some popular browsers with known fixed-positioning issues
+ // This is a plugin option like any other, so feel free to improve or overwrite it
+ supportBlacklist: function () {
+ var w = window,
+ ua = navigator.userAgent,
+ platform = navigator.platform,
+ // Rendering engine is Webkit, and capture major version
+ wkmatch = ua.match( /AppleWebKit\/([0-9]+)/ ),
+ wkversion = !!wkmatch && wkmatch[ 1 ],
+ ffmatch = ua.match( /Fennec\/([0-9]+)/ ),
+ ffversion = !!ffmatch && ffmatch[ 1 ],
+ operammobilematch = ua.match( /Opera Mobi\/([0-9]+)/ ),
+ omversion = !!operammobilematch && operammobilematch[ 1 ];
+
+ if (
+ // iOS 4.3 and older : Platform is iPhone/Pad/Touch and Webkit version is less than 534 (ios5)
+ ( ( platform.indexOf( "iPhone" ) > -1 || platform.indexOf( "iPad" ) > -1 || platform.indexOf( "iPod" ) > -1 ) && wkversion && wkversion < 534 ) ||
+ // Opera Mini
+ ( w.operamini && ({}).toString.call( w.operamini ) === "[object OperaMini]" ) ||
+ ( operammobilematch && omversion < 7458 ) ||
+ //Android lte 2.1: Platform is Android and Webkit version is less than 533 (Android 2.2)
+ ( ua.indexOf( "Android" ) > -1 && wkversion && wkversion < 533 ) ||
+ // Firefox Mobile before 6.0 -
+ ( ffversion && ffversion < 6 ) ||
+ // WebOS less than 3
+ ( window.palmGetResource !== undefined && wkversion && wkversion < 534 ) ||
+ // MeeGo
+ ( ua.indexOf( "MeeGo" ) > -1 && ua.indexOf( "NokiaBrowser/8.5.0" ) > -1 )
+ ) {
+ return true;
+ }
+
+ return false;
+ },
+ initSelector: ":jqmData(role='content')"
},
- _increaseRow : function ( num ) {
+ _create: function () {
+
var self = this,
- rotation = self.options.rotation,
- totalRowCnt = self._totalRowCnt,
- rowView = self._$view[ 0 ],
- firstRow = null,
- lastRow = rowView.lastChild,
- row = null,
- headRowIndex = 0,
- tailRowIndex = 0,
- i;
+ o = self.options,
+ $el = self.element;
- if ( !lastRow ) {
+ // Feature detecting support for
+ if ( o.supportBlacklist() ) {
+ self.destroy();
return;
}
- tailRowIndex = parseInt( lastRow.getAttribute( "row-index" ), 10 );
- if ( !rotation ) {
- firstRow = rowView.firstChild;
- headRowIndex = parseInt( firstRow.getAttribute( "row-index" ), 10 );
+ self._addFixedClass();
+ self._addTransitionClass();
+ self._bindPageEvents();
+
+ // only content
+ self._bindContentControlEvents();
+
+ // Store back-button, to show again
+ self._backBtnQueue = [];
+ },
+
+ /* add minimum fixed css style to bar(header/footer) and content
+ * it need to update when core source modified(jquery.mobile.page.section.js)
+ * modified from core source cuz initSelector different */
+ _addFixedClass: function () {
+ var self = this,
+ o = self.options,
+ $el = self.element,
+ $elHeader = $el.siblings( ":jqmData(role='header')" ),
+ $elFooter = $el.siblings( ":jqmData(role='footer')" ),
+ $elPage = $el.closest(".ui-page");
+
+ $elHeader.addClass( "ui-header-fixed" );
+ $elFooter.addClass( "ui-footer-fixed" );
+
+ // "fullscreen" overlay positioning
+ if ( o.fullscreen ) {
+ $elHeader.addClass( "ui-header-fullscreen" );
+ $elFooter.addClass( "ui-footer-fullscreen" );
+ $elPage
+ .addClass( "ui-page-header-fullscreen" )
+ .addClass( "ui-page-footer-fullscreen" );
+ } else {
+ // If not fullscreen, add class to page to set top or bottom padding
+ $elPage.addClass( "ui-page-header-fixed" )
+ .addClass( "ui-page-footer-fixed" );
}
+ },
- for ( i = 0 ; i < num ; ++i ) {
- if ( tailRowIndex >= totalRowCnt - 1 && !rotation ) {
- if ( headRowIndex == 0 ) {
- break;
- }
+ /* original core source(jquery.mobile.fixedToolbar.js)
+ * never changed */
+ _addTransitionClass: function () {
+ var tclass = this.options.transition;
- row = self._makeRow( --headRowIndex );
- rowView.insertBefore( row, firstRow );
- firstRow = row;
- } else {
- row = self._makeRow( circularNum( ++tailRowIndex, totalRowCnt ) );
- rowView.appendChild( row );
+ if ( tclass && tclass !== "none" ) {
+ // use appropriate slide for header or footer
+ if ( tclass === "slide" ) {
+ tclass = this.element.is( ".ui-header" ) ? "slidedown" : "slideup";
}
- if ( self._direction ) {
- $( row ).width( self._cellSize );
- } else {
- $( row ).height( self._cellSize );
- }
+ this.element.addClass( tclass );
}
},
- _decreaseRow : function ( num ) {
- var self = this,
- rowView = self._$view[ 0 ],
- i;
- for ( i = 0 ; i < num ; ++i ) {
- rowView.removeChild( rowView.lastChild );
- }
- },
+ /* Set default page positon
+ * 1. add title style to header
+ * 2. Set default header/footer position */
+ setHeaderFooter: function ( thisPage ) {
+ var $elPage = $( thisPage ),
+ $elHeader = $elPage.find( ":jqmData(role='header')" ).length ? $elPage.find( ":jqmData(role='header')") : $elPage.siblings( ":jqmData(role='header')"),
+ $elContent = $elPage.find( ".ui-content" ),
+ $elFooter = $elPage.find( ":jqmData(role='footer')" ),
+ $elFooterGroup = $elFooter.find( ":jqmData(role='fieldcontain')" ),
+ $elFooterControlGroup = $elFooter.find( ".ui-controlgroup" );
- _replaceRows : function ( curCnt, prevCnt, maxCnt, clipPosition ) {
- var self = this,
- $rows = self._$view.children(),
- prevRowIndex = 0,
- rowIndex = 0,
- diffRowCnt = 0,
- targetCnt = 1,
- filterCondition = ( self._filterRatio * self._cellSize ) + self._cellSize,
- idx = 0;
+ // divide content mode scrollview and non-scrollview
+ if ( !$elPage.is( ".ui-dialog" ) ) {
+ if ( $elHeader.jqmData("position") == "fixed" || ( $.support.scrollview && $.tizen.frameworkData.theme.match(/tizen/) ) ) {
+ $elHeader
+ .css( "position", "fixed" )
+ .css( "top", "0px" );
+ } else if ( !$.support.scrollview && $elHeader.jqmData("position") != "fixed" ) {
+ $elHeader.css( "position", "relative" );
+ }
+ }
- if ( filterCondition < clipPosition ) {
- targetCnt += 1;
+ /* set Title style */
+ if ( $elHeader.find("span.ui-title-text-sub").length ) {
+ $elHeader.addClass( "ui-title-multiline");
}
- prevRowIndex = parseInt( $( $rows[targetCnt] ).attr( "row-index" ), 10 );
- if ( prevRowIndex === 0 ) {
- // only top.
- rowIndex = maxCnt - targetCnt;
- } else {
- rowIndex = Math.round( ( prevRowIndex * prevCnt ) / curCnt );
- if ( rowIndex + self._rowsPerView >= maxCnt ) {
- // only bottom.
- rowIndex = maxCnt - self._rowsPerView;
- }
- diffRowCnt = prevRowIndex - rowIndex;
- rowIndex -= targetCnt;
+ if ( $elFooterGroup.find( "div" ).is( ".ui-controlgroup-label" ) ) {
+ $elFooterGroup.find( "div.ui-controlgroup-label" ).remove();
}
- for ( idx = 0 ; idx < $rows.length ; idx += 1 ) {
- self._replaceRow( $rows[idx], circularNum( rowIndex, self._totalRowCnt ) );
- rowIndex++;
+ if ( $elFooterControlGroup.length ) {
+ var anchorPer = 100 / $elFooterControlGroup.find( "a" ).length;
+ $elFooterControlGroup.find( "a" ).each( function ( i ) {
+ $elFooterControlGroup.find( "a" ).eq( i ).width( anchorPer + "%" );
+ });
}
- return -diffRowCnt;
},
- _replaceRow : function ( block, index ) {
+ _bindPageEvents: function () {
var self = this,
- tempBlocks = null;
+ o = self.options,
+ $el = self.element,
+ $elCurrentFooter;
- while ( block.hasChildNodes() ) {
- block.removeChild( block.lastChild );
- }
+ //page event bindings
+ // Fixed toolbars require page zoom to be disabled, otherwise usability issues crop up
+ // This method is meant to disable zoom while a fixed-positioned toolbar page is visible
+ $el.closest( ".ui-page" )
+ .bind( "pagebeforeshow", function ( event ) {
+ var thisPage = this;
+ if ( o.disablePageZoom ) {
+ $.mobile.zoom.disable( true );
+ }
+ if ( !o.visibleOnPageShow ) {
+ self.hide( true );
+ }
+ self.setHeaderFooter( thisPage );
+ self._setContentMinHeight( thisPage );
+ } )
+ .bind( "webkitAnimationStart animationstart updatelayout", function ( e, data ) {
+ var thisPage = this;
+ if ( o.updatePagePadding ) {
+ self.updatePagePadding(thisPage);
+ self.updatePageLayout( thisPage, data);
+ }
+ })
- tempBlocks = self._makeRow( index );
- while ( tempBlocks.children.length ) {
- block.appendChild( tempBlocks.children[0] );
- }
- block.setAttribute( "row-index", tempBlocks.getAttribute( "row-index" ) );
- tempBlocks.parentNode.removeChild( tempBlocks );
- },
+ .bind( "pageshow", function ( event ) {
+ var thisPage = this;
+ self._setContentMinHeight( thisPage );
+ self.updatePagePadding( thisPage );
+ self._updateHeaderArea( thisPage );
+ if ( o.updatePagePadding ) {
+ $( window ).bind( "throttledresize." + self.widgetName, function () {
+ self.updatePagePadding(thisPage);
- _createElement : function ( tag ) {
- var element = document.createElement( tag );
+ self.updatePageLayout( thisPage, false);
+ self._updateHeaderArea( thisPage );
+ self._setContentMinHeight( thisPage );
+ });
+ }
+ })
- this._fragment.appendChild( element );
- return element;
- },
+ .bind( "pagebeforehide", function ( e, ui ) {
+ if ( o.disablePageZoom ) {
+ $.mobile.zoom.enable( true );
+ }
+ if ( o.updatePagePadding ) {
+ $( window ).unbind( "throttledresize." + self.widgetName );
+ }
+ });
- _getObjectNames : function ( obj ) {
- var properties = [],
- name = "";
+ window.addEventListener( "softkeyboardchange", function ( e ) {
+ var $elDownBtn = $( "<div class='ui-btn-footer-down'></div>" ),
+ $elPage = $( ".ui-page-active" ),
+ backBtn,
+ backBtnPosition = "footer";
- for ( name in obj ) {
- properties.push( name );
- }
- this._properties = properties;
- },
+ if ( $elPage.data( "addBackBtn" ) ) {
+ $elPage.data( "addBackBtn" ) == "header" ? backBtnPosition = "header" : backBtnPosition = "footer";
- _getConvertedTmplStr : function ( data ) {
- var self = this,
- dataProperties = self._properties,
- i = 0,
- plainMsg,
- ret = "";
+ if ( e.state == "on" ) {
+ if ( !$elPage.find( ".ui-" + backBtnPosition + " .ui-btn-footer-down" ).length ) {
+ $elDownBtn.buttonMarkup( { icon: "down" } ).appendTo( $elPage.find( ".ui-" + backBtnPosition ) );
+ }
- if ( !data ) {
- return ;
- }
+ // N_SE-32900: If an app moves a page when the pop is shown, the .ui-page-active page
+ // is changed.
+ // In this case, the '.ui-page-active .ui-btn-back' selector indicates a
+ // new page's one, and the old page's .ui-btn-back button is still hidden.
+ // So, the current back button is remembered to be shown at the
+ // softkeyboardchange.off event.
+ backBtn = $( ".ui-page-active .ui-btn-back" );
+ backBtn.hide();
+ self._backBtnQueue.push( backBtn ); // Store hidden backBtn
+ } else if ( e.state == "off" ) {
+ self._backBtnQueue.forEach( function ( b ) {
+ b.show(); // Show each backBtn,
+ } );
+ self._backBtnQueue.length = 0; // and clear queue.
- plainMsg = self._templateText;
- for ( i = 0; i < dataProperties.length; i++ ) {
- plainMsg = self._strReplace( plainMsg, "${" + dataProperties[ i ] + "}" , data[ dataProperties[ i ] ] );
- }
- plainMsg = self._changeImgSrcAriaAttrFromTmpl( plainMsg );
+ $( ".ui-btn-footer-down" ).remove();
+ }
+ }
- return plainMsg;
+ });
},
- _changeImgSrcAriaAttrFromTmpl : function ( plainMsg ) {
+ _bindContentControlEvents: function () {
var self = this,
- ret = "",
- targetTagIdx,
- beforeTargetTag = "",
- afterTargetTag = "",
- imgFileName,
- imgSrcSlashIdx,
- temp,
- srcRegExpResult;
+ o = self.options,
+ $el = self.element;
- temp = plainMsg;
- targetTagIdx = temp.indexOf( "$ARIA-IMG-SRC-ALT$" );
- while ( targetTagIdx !== -1 ) {
- imgFileName = "";
- beforeTargetTag = beforeTargetTag + temp.slice( 0, targetTagIdx + 19 );
- afterTargetTag = temp.slice( targetTagIdx + 19, temp.length );
- srcRegExpResult = afterTargetTag.match( imgTagSrcAttrRE );
- if ( srcRegExpResult ) {
- imgSrcSlashIdx = srcRegExpResult[0].lastIndexOf( "/" );
- if ( imgSrcSlashIdx !== -1 ) {
- imgFileName = srcRegExpResult[0].slice( imgSrcSlashIdx + 1, -1 );
- }
- }
- beforeTargetTag = beforeTargetTag.replace( "$ARIA-IMG-SRC-ALT$", imgFileName );
- temp = afterTargetTag;
- targetTagIdx = temp.indexOf( "$ARIA-IMG-SRC-ALT$" );
- ret = beforeTargetTag + afterTargetTag;
+ $el.closest( ".ui-page" )
+ .bind( "pagebeforeshow", function ( event ) {
+
+ });
+ },
+
+ _setContentMinHeight : function ( thisPage ) {
+ var $elPage = $( thisPage ),
+ $elHeader = $elPage.find( ":jqmData(role='header')" ),
+ $elFooter = $elPage.find( ":jqmData(role='footer')" ),
+ $elContent = $elPage.find( ":jqmData(role='content')" ),
+ resultMinHeight,
+ dpr = 1,
+ layoutInnerHeight = window.innerHeight;
+
+ if ( !$.support.scrollview || ($.support.scrollview && $elContent.jqmData("scroll") === "none") ) {
+ dpr = window.outerWidth / window.innerWidth;
+ layoutInnerHeight = Math.floor( window.outerHeight / dpr );
+ } else {
+ layoutInnerHeight = window.innerHeight;
}
- if ( ret === "" ) {
- ret = plainMsg;
- }
+ resultMinHeight = layoutInnerHeight - $elHeader.height() - $elFooter.height();
- return ret;
+ if ( $.support.scrollview && $elContent.jqmData("scroll") !== "none" ) {
+ $elContent.css( "min-height", resultMinHeight - parseFloat( $elContent.css("padding-top") ) - parseFloat( $elContent.css("padding-bottom") ) + "px" );
+ $elContent.children( ".ui-scrollview-view" ).css( "min-height", $elContent.css( "min-height" ) );
+ }
},
- _insertAriaAttrToTmpl : function ( plainMsg ) {
- var ret = "",
- targetTagIdx,
- beforeTargetTag = "",
- afterTargetTag = "",
- temp;
+ _updateHeaderArea : function ( thisPage ) {
+ var $elPage = $( thisPage ),
+ $elHeader = $elPage.find( ":jqmData(role='header')" ).length ? $elPage.find( ":jqmData(role='header')") : $elPage.siblings( ":jqmData(role='header')"),
+ headerBtnNum = $elHeader.children("a").length,
+ headerSrcNum = $elHeader.children("img").length;
- temp = plainMsg.replace( "<div", "<div tabindex=\"0\" aria-selected=\"true\"" );
- targetTagIdx = temp.indexOf( "<img" );
- if ( targetTagIdx !== -1 ) {
- while ( targetTagIdx !== -1 ) {
- beforeTargetTag = beforeTargetTag + temp.slice( 0, targetTagIdx + 4 );
- afterTargetTag = temp.slice( targetTagIdx + 4, temp.length );
- beforeTargetTag = beforeTargetTag + " role=\"img\" alt=\"$ARIA-IMG-SRC-ALT$\"";
- temp = afterTargetTag;
- targetTagIdx = temp.indexOf( "<img" );
- ret = beforeTargetTag + afterTargetTag;
- }
- temp = ret;
- targetTagIdx = temp.indexOf( "<span" );
- beforeTargetTag = "";
- while ( targetTagIdx !== -1 ) {
- beforeTargetTag = beforeTargetTag + temp.slice( 0, targetTagIdx + 5 );
- afterTargetTag = temp.slice( targetTagIdx + 5, temp.length );
- beforeTargetTag = beforeTargetTag + " aria-hidden=\"true\" tabindex=\"-1\"";
- temp = afterTargetTag;
- targetTagIdx = temp.indexOf( "<span" );
- ret = beforeTargetTag + afterTargetTag;
- }
+ if ( !$elPage.is( ".ui-dialog" ) ) {
+ $elHeader.find( "h1" ).css( "width", window.innerWidth - parseInt( $elHeader.find( "h1" ).css( "margin-left" ), 10 ) * 2 - $elHeader.children( "a" ).width() * headerBtnNum - $elHeader.children( "a" ).width() / 4 - $elHeader.children( "img" ).width() * headerSrcNum * 4 );
}
+ /* add half width for default space between text and button, and img tag area is too narrow, so multiply three for img width*/
+ },
- if ( ret === "" ) {
- ret = plainMsg;
- }
+ _visible: true,
- return ret;
- },
+ // This will set the content element's top or bottom padding equal to the toolbar's height
+ updatePagePadding: function ( tbPage ) {
+ var $el = this.element,
+ header = $el.siblings( ".ui-header" ).length,
+ footer = $el.siblings( ".ui-footer" ).length;
- _strReplace : function ( plainMsg, stringToFind, stringToReplace ) {
- var temp = plainMsg,
- index = plainMsg.indexOf( stringToFind );
- while ( index !== -1 ) {
- temp = temp.replace( stringToFind, stringToReplace );
- index = temp.indexOf( stringToFind );
+ // This behavior only applies to "fixed", not "fullscreen"
+ if ( this.options.fullscreen ) {
+ return;
}
- return temp;
- }
- } );
+ tbPage = tbPage || $el.closest( ".ui-page" );
- $( document ).bind( "pagecreate create", function ( e ) {
- $( ":jqmData(role='virtualgrid')" ).virtualgrid();
- } );
-} ( jQuery, window, document ) );
+ if ( $el.siblings( ".ui-header" ).jqmData("position") == "fixed" || ($.support.scrollview && $el.jqmData("scroll") !== "none" )) {
+ $( tbPage ).css( "padding-top", ( header ? $el.siblings( ".ui-header" ).outerHeight() : 0 ) );
+ }
+ $( tbPage ).css( "padding-bottom", ( footer ? $el.siblings( ".ui-footer" ).outerHeight() : 0 ) );
+ },
+ /* 1. Calculate and update content height */
+ updatePageLayout: function ( thisPage, receiveType ) {
+ var $elFooter,
+ $elPage = $( thisPage ),
+ $elHeader = $elPage.find( ":jqmData(role='header')" ),
+ $elContent = $elPage.find( ":jqmData(role='content')" ),
+ resultContentHeight = 0,
+ resultFooterHeight = 0,
+ resultHeaderHeight = 0,
+ layoutInnerHeight = window.innerHeight,
+ dpr = 1;
+ if ( $elPage.length ) {
+ $elFooter = $elPage.find( ":jqmData(role='footer')" );
+ } else {
+ $elFooter = $( document ).find( ":jqmData(role='footer')" ).eq( 0 );
+ }
-(function($, undefined) {
+ // calculate footer height
+ resultFooterHeight = ( $elFooter.css( "display" ) == "none" || $elFooter.length == 0 ) ? 0 : $elFooter.height();
+ resultHeaderHeight = ( $elHeader.css( "display" ) == "none" || $elHeader.length == 0 ) ? 0 : $elHeader.height();
-ensureNS("jQuery.mobile.tizen");
+ if (resultFooterHeight != 0 ) {
+ $elFooter.css( "bottom", 0 );
+ }
-jQuery.extend( jQuery.mobile.tizen,
-{
- _widgetPrototypes: {},
+ if ( !$.support.scrollview || ($.support.scrollview && $elContent.jqmData("scroll") === "none") ) {
+ dpr = window.outerWidth / window.innerWidth;
+ layoutInnerHeight = Math.floor( window.outerHeight / dpr );
+ } else {
+ layoutInnerHeight = window.innerHeight;
+ }
- /*
- * load the prototype for a widget.
- *
- * If @widget is a string, the function looks for @widget.prototype.html in the proto-html/ subdirectory of the
- * framework's current theme and loads the file via AJAX into a string. Note that the file will only be loaded via
- * AJAX once. If two widget instances based on the same @widget value are to be constructed, the second will be
- * constructed from the cached copy of the prototype of the first instance.
- *
- * If @widget is not a string, it is assumed to be a hash containing at least one key, "proto", the value of which is
- * the string to be used for the widget prototype. if another key named "key" is also provided, it will serve as the
- * key under which to cache the prototype, so it need not be rendered again in the future.
- *
- * Given the string for the widget prototype, the following patterns occurring in the string are replaced:
- *
- * "${FRAMEWORK_ROOT}" - replaced with the path to the root of the framework
- *
- * The function then creates a jQuery $("<div>") object containing the prototype from the string.
- *
- * If @ui is not provided, the jQuery object containing the prototype is returned.
- *
- * If @ui is provided, it is assumed to be a (possibly multi-level) hash containing CSS selectors. For every level of
- * the hash and for each string-valued key at that level, the CSS selector specified as the value is sought in the
- * prototype jQuery object and, if found, the value of the key is replaced with the jQuery object resulting from the
- * search. Additionally, if the CSS selector is of the form "#widgetid", the "id" attribute will be removed from the
- * elements contained within the resulting jQuery object. The resulting hash is returned.
- *
- * Examples:
- *
- * 1.
- * $.mobile.tizen.loadPrototype("mywidget") => Returns a <div> containing the structure from the file
- * mywidget.prototype.html located in the current theme folder of the current framework.
- *
- * 2. $.mobile.tizen.loadPrototype("mywidget", ui):
- * where ui is a hash that looks like this:
- * ui = {
- * element1: "<css selector 1>",
- * element2: "<css selector 2>",
- * group1: {
- * group1element1: "<css selector 3>",
- * group1element1: "<css selector 4>"
- * }
- * ...
- * }
- *
- * In this case, after loading the prototype as in Example 1, loadPrototype will traverse @ui and replace the CSS
- * selector strings with the result of the search for the selector string upon the prototype. If any of the CSS
- * selectors are of the form "#elementid" then the "id" attribute will be stripped from the elements selected. This
- * means that they will no longer be accessible via the selector used initially. @ui is then returned thus modified.
- */
+ resultContentHeight = layoutInnerHeight - resultFooterHeight - resultHeaderHeight;
- loadPrototype: function(widget, ui) {
- var ret = undefined,
- theScriptTag = $("script[data-framework-version][data-framework-root][data-framework-theme]"),
- frameworkRootPath = theScriptTag.attr("data-framework-root") + "/" +
- theScriptTag.attr("data-framework-version") + "/";
+ if ( $.support.scrollview && $elContent.jqmData("scroll") !== "none" ) {
+ $elContent.height( resultContentHeight -
+ parseFloat( $elContent.css("padding-top") ) -
+ parseFloat( $elContent.css("padding-bottom") ) );
+ }
- function replaceVariables(s) {
- return s.replace(/\$\{FRAMEWORK_ROOT\}/g, frameworkRootPath);
- }
+ // External call page( "refresh") - in case title changed
+ if ( receiveType ) {
+ $elPage
+ .css( "min-height", resultContentHeight )
+ .css( "padding-top", resultHeaderHeight )
+ .css( "padding-bottom", resultFooterHeight );
+ }
+ },
- function fillObj(obj, uiProto) {
- var selector;
+ show: function ( notransition ) {
+ /* blank function: deprecated */
+ },
- for (var key in obj) {
- if (typeof obj[key] === "string") {
- selector = obj[key];
- obj[key] = uiProto.find(obj[key]);
- if (selector.substring(0, 1) === "#")
- obj[key].removeAttr("id");
- }
- else
- if (typeof obj[key] === "object")
- obj[key] = fillObj(obj[key], uiProto);
- }
- return obj;
- }
+ hide: function ( notransition ) {
+ /* blank function: deprecated */
+ },
- /* If @widget is a string ... */
- if (typeof widget === "string") {
- /* ... try to use it as a key into the cached prototype hash ... */
- ret = $.mobile.tizen._widgetPrototypes[widget];
- if (ret === undefined) {
- /* ... and if the proto was not found, try to load its definition ... */
- var protoPath = frameworkRootPath + "proto-html" + "/" +
- theScriptTag.attr("data-framework-theme");
- $.ajax({
- url: protoPath + "/" + widget + ".prototype.html",
- async: false,
- dataType: "html"
- })
- .success(function(data, textStatus, jqXHR) {
- /* ... and if loading succeeds, cache it and use a copy of it ... */
- $.mobile.tizen._widgetPrototypes[widget] = $("<div>").html(replaceVariables(data));
- ret = $.mobile.tizen._widgetPrototypes[widget].clone();
- });
- }
- }
- /* Otherwise ... */
- else {
- /* ... if a key was provided ... */
- if (widget.key !== undefined)
- /* ... try to use it as a key into the cached prototype hash ... */
- ret = $.mobile.tizen._widgetPrototypes[widget.key];
+ toggle: function () {
+ this[ this._visible ? "hide" : "show" ]();
+ },
- /* ... and if the proto was not found in the cache ... */
- if (ret === undefined) {
- /* ... and a proto definition string was provided ... */
- if (widget.proto !== undefined) {
- /* ... create a new proto from the definition ... */
- ret = $("<div>").html(replaceVariables(widget.proto));
- /* ... and if a key was provided ... */
- if (widget.key !== undefined)
- /* ... cache a copy of the proto under that key */
- $.mobile.tizen._widgetPrototypes[widget.key] = ret.clone();
- }
- }
- else
- /* otherwise, if the proto /was/ found in the cache, return a copy of it */
- ret = ret.clone();
- }
+ destroy: function () {
+ this.element.removeClass( "ui-header-fixed ui-footer-fixed ui-header-fullscreen ui-footer-fullscreen in out fade slidedown slideup ui-fixed-hidden" );
+ this.element.closest( ".ui-page" ).removeClass( "ui-page-header-fixed ui-page-footer-fixed ui-page-header-fullscreen ui-page-footer-fullscreen" );
+ },
- /* If the prototype was found/created successfully ... */
- if (ret != undefined)
- /* ... and @ui was provided */
- if (ui != undefined)
- /* ... return @ui, but replace the CSS selectors it contains with the elements they select */
- ret = fillObj(ui, ret);
+ refresh: function () {
+ var $elPage = $( ".ui-page-active" );
+ this.setHeaderFooter( $elPage );
+ this._updateHeaderArea( $elPage );
+ }
+ });
- return ret;
- }
-});
-})(jQuery);
+ //auto self-init widgets
+ $( document )
+ .bind( "pagecreate create", function ( e ) {
+ // DEPRECATED in 1.1: support for data-fullscreen=true|false on the page element.
+ // This line ensures it still works, but we recommend moving the attribute to the toolbars themselves.
+ if ( $( e.target ).jqmData( "fullscreen" ) ) {
+ $( $.mobile.pagelayout.prototype.options.initSelector, e.target ).not( ":jqmData(fullscreen)" ).jqmData( "fullscreen", true );
+ }
+ $.mobile.pagelayout.prototype.enhanceWithin( e.target );
+ });
+}( jQuery ));
-/* ***************************************************************************
+
+/*
+ * jQuery Mobile Widget @VERSION
+ *
+ * This software is licensed under the MIT licence (as defined by the OSI at
+ * http://www.opensource.org/licenses/mit-license.php)
+ *
+ * ***************************************************************************
* Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2011 by Intel Corporation Ltd.
*
* Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software" ),
+ * copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* DEALINGS IN THE SOFTWARE.
* ***************************************************************************
*
- * Author: Minkyu Kang <mk7.kang@samsung.com>
- * Author: Koeun Choi <koeun.choi@samsung.com>
+ * Authors: Max Waterman <max.waterman@intel.com>
+ * Authors: Minkyu Kang <mk7.kang@samsung.com>
*/
-/*
- * Progress widget
- *
- * HTML Attributes
- *
- * data-role: set to 'progress'.
- * data-style: 'circle' or 'pending'.
+/**
+ * tizenslider modifies the JQuery Mobile slider and is created in the same way.
*
- * APIs
+ * See the JQuery Mobile slider widget for more information :
+ * http://jquerymobile.com/demos/1.0a4.1/docs/forms/forms-slider.html
*
- * show(): show the progress.
- * hide(): hide the progress.
- * running(boolean): start or stop the running.
+ * The JQuery Mobile slider option:
+ * theme: specify the theme using the 'data-theme' attribute
*
- * Events
+ * Options:
+ * theme: string; the theme to use if none is specified using the 'data-theme' attribute
+ * default: 'c'
+ * popup: boolean; controls whether the popup is displayed or not
+ * specify if the popup is enabled using the 'data-popup' attribute
+ * set from javascript using .tizenslider('option','popup',newValue)
*
- * N/A
+ * Events:
+ * changed: triggers when the value is changed (rather than when the handle is moved)
*
- * Examples
+ * Examples:
*
- * <li data-role="list-divider">Progress Pending</li>
- * <li>
- * <div data-role="progress" data-style="pending" id="pending"></div>
- * </li>
- * <li data-role="list-divider">Progress ~ing</li>
- * <li>
- * <div data-role="progress" data-style="circle" id="progress"></div>Loading..
- * </li>
+ * <a href="#" id="popupEnabler" data-role="button" data-inline="true">Enable popup</a>
+ * <a href="#" id="popupDisabler" data-role="button" data-inline="true">Disable popup</a>
+ * <div data-role="fieldcontain">
+ * <input id="mySlider" data-theme='a' data-popup='false' type="range" name="slider" value="7" min="0" max="9" />
+ * </div>
+ * <div data-role="fieldcontain">
+ * <input id="mySlider2" type="range" name="slider" value="77" min="0" max="777" />
+ * </div>
*
- * $("#pending").progress( "running", true );
- * $("#progress").progress( "running", true );
+ * // disable popup from javascript
+ * $('#mySlider').tizenslider('option','popup',false);
*
+ * // from buttons
+ * $('#popupEnabler').bind('vclick', function() {
+ * $('#mySlider').tizenslider('option','popup',true);
+ * });
+ * $('#popupDisabler').bind('vclick', function() {
+ * $('#mySlider').tizenslider('option','popup',false);
+ * });
*/
/**
- @class Progress
- The progress widget shows that an operation is in progress. <br/>To add a progress widget to the application, use the following code:
+ @class Slider
+ The slider widget shows a control on the screen that you can use to change values by dragging a handle on a horizontal scale. Sliders can be used in Tizen as described in the jQueryMobile documentation for sliders.
- <div data-role="progress" data-style="circle"></div>
+ To add a slider widget to the application, use the following code:
+
+ <input data-popup='false' type="range" name="slider" value="5" min="0" max="10" data-icon="text" data-text-left="Min" data-text-right="Max" />
+
+ The slider can define callbacks for events as described in the jQueryMobile documentation for slider events.
+ You can use methods with the slider as described in the jQueryMobile documentation for slider methods.
*/
/**
- @property {String} data-style
- Sets the style of the progress widget. The style options are pending (pending progress style) and circle (circular progress status style).
+ @property {String} data-icon
+ Defines the icon style for the slider ends. The icon options are bright, volume, and text.
+ The default value is text.
*/
/**
- @method running
- The running method is used to set the current running state of the pending or circular progress widget:
-
- <div id="foo" data-role="progress" data-style="pending"></div>
- $("#foo").progress("running", true);
+ @property {Boolean} data-popup
+ Enables or disables a pop-up showing the current value while the handle is dragged.
+ The default value is true.
*/
/**
- @method show
- The show method is used to show the pending or circular progress widget:
-
- <div id="foo" data-role="progress" data-style="pending"></div>
- $("#foo").progress("show");
+ @property {String} data-text-left
+ Defines the text displayed on the left side of the slider.
+ The data-icon option must be set to text.
*/
/**
- @method hide
- The show method is used to hide the pending or circular progress widget:
+ @property {String} data-text-right
+ Defines the text displayed on the right side of the slider.
+ The data-icon option must be set to text.
+*/
+
+(function ($, window, undefined) {
+ $.widget("tizen.tizenslider", $.mobile.widget, {
+ options: {
+ popup: true
+ },
+
+ popup: null,
+ handle: null,
+ handleText: null,
+
+ _create: function () {
+ this.currentValue = null;
+ this.popupVisible = false;
+
+ var self = this,
+ inputElement = $( this.element ),
+ slider,
+ handle_press,
+ popupEnabledAttr,
+ icon,
+ text_right,
+ text_left,
+ text_length,
+ elem_left,
+ elem_right,
+ margin_left,
+ margin_right;
+
+ // apply jqm slider
+ inputElement.slider();
+
+ // hide the slider input element proper
+ inputElement.hide();
+
+ self.popup = $('<div class="ui-slider-popup"></div>');
+
+ // set the popup according to the html attribute
+ popupEnabledAttr = inputElement.jqmData('popup');
+ if ( popupEnabledAttr !== undefined ) {
+ self.options.popup = ( popupEnabledAttr == true );
+ }
+
+ // get the actual slider added by jqm
+ slider = inputElement.next('.ui-slider');
+
+ icon = inputElement.attr('data-icon');
+
+ // wrap the background
+ slider.wrap('<div class="ui-slider-container"></div>');
+
+ // get the handle
+ self.handle = slider.find('.ui-slider-handle');
+
+ // remove the rounded corners from the slider and its children
+ slider.removeClass('ui-btn-corner-all');
+ slider.find('*').removeClass('ui-btn-corner-all');
+
+ // add icon
+ switch ( icon ) {
+ case 'bright':
+ case 'volume':
+ elem_left = $('<div class="ui-slider-left-' + icon + '"></div>');
+ elem_right = $('<div class="ui-slider-right-' + icon + '"></div>');
+
+ slider.before( elem_left );
+ slider.after( elem_right );
+
+ margin_left = elem_left.width() + 16;
+ margin_right = elem_right.width() + 16;
+ break;
+
+ case 'text':
+ text_left = ( inputElement.attr('data-text-left') === undefined ) ? '' :
+ inputElement.attr('data-text-left').substring( 0, 3 );
+ text_right = ( inputElement.attr('data-text-right') === undefined ) ? '' :
+ inputElement.attr('data-text-right').substring( 0, 3 );
+
+ text_length = Math.max( text_left.length, text_right.length ) + 1;
+
+ margin_left = text_length + "rem";
+ margin_right = text_length + "rem";
+
+ elem_left = $('<div class="ui-slider-left-text" style="left:' +
+ -( text_length ) + 'rem; width:' + text_length + 'rem;">' +
+ '<span style="position:relative;top:0.4em;">' +
+ text_left +
+ '</span></div>');
+ elem_right = $('<div class="ui-slider-right-text" style="right:' +
+ -( text_length ) + 'rem; width:' + text_length + 'rem;">' +
+ '<span style="position:relative;top:0.4em;">' +
+ text_right +
+ '</span></div>');
+
+ slider.before( elem_left );
+ slider.after( elem_right );
+ break;
+ }
+
+ if ( icon ) {
+ slider.parent('.ui-slider-container').css({
+ "margin-left": margin_left,
+ "margin-right": margin_right
+ });
+ }
+
+ // handle press
+ slider.append($('<div class="ui-slider-handle-press"></div>'));
+ self.handle_press = slider.find('.ui-slider-handle-press');
+ self.handle_press.css('display', 'none');
+
+ // add a popup element (hidden initially)
+ slider.parents(".ui-page").append( self.popup );
+ self.popup.hide();
+
+ // get the element where value can be displayed
+ self.handleText = slider.find('.ui-btn-text');
+
+ // set initial value
+ self.updateSlider();
- <div id="foo" data-role="progress" data-style="pending"></div>
- $("#foo").progress("hide");
-*/
+ // bind to changes in the slider's value to update handle text
+ this.element.bind('change', function () {
+ self.updateSlider();
+ });
-(function ( $, window, undefined ) {
- $.widget( "tizen.progress", $.mobile.widget, {
- options: {
- style: "circle",
- running: false
+ // bind clicks on the handle to show the popup
+ self.handle.bind('vmousedown', function () {
+ self.showPopup();
+ });
+
+ // watch events on the document to turn off the slider popup
+ slider.add( document ).bind('vmouseup', function () {
+ self.hidePopup();
+ });
},
- show: function () {
- $( this.element ).show();
+ _handle_press_show: function () {
+ this.handle_press.css('display', '');
},
- hide: function () {
- $( this.element ).hide();
+ _handle_press_hide: function () {
+ this.handle_press.css('display', 'none');
},
- _start: function () {
- if ( !this.init ) {
- $( this.element ).append( this.html );
- this.init = true;
- }
+ // position the popup
+ positionPopup: function () {
+ var dstOffset = this.handle.offset();
- this.show();
+ this.popup.offset({
+ left: dstOffset.left + ( this.handle.width() - this.popup.width() ) / 2,
+ top: dstOffset.top - this.popup.height()
+ });
- $( this.element )
- .find( ".ui-progress-" + this.options.style )
- .addClass( this.runningClass );
+ this.handle_press.offset({
+ left: dstOffset.left,
+ top: dstOffset.top
+ });
},
- _stop: function () {
- $( this.element )
- .find( ".ui-progress-" + this.options.style )
- .removeClass( this.runningClass );
- },
+ // show value on the handle and in popup
+ updateSlider: function () {
+ var font_size,
+ font_length,
+ font_top,
+ padding_size,
+ newValue,
+ get_value_length = function ( v ) {
+ var val = Math.abs( v ),
+ len;
- running: function ( running ) {
- if ( running === undefined ) {
- return this.options.running;
- }
+ if ( val > 999 ) {
+ len = 4;
+ } else if ( val > 99 ) {
+ len = 3;
+ } else if ( val > 9 ) {
+ len = 2;
+ } else {
+ len = 1;
+ }
- this._setOption( "running", running );
- },
+ if ( v < 0 ) {
+ len++;
+ }
- _setOption: function ( key, value ) {
- if ( key === "running" ) {
- if ( typeof value !== "boolean" ) {
- window.alert( "running value MUST be boolean type!" );
- return;
+ return len;
+ };
+
+ // remove the title attribute from the handle (which is
+ // responsible for the annoying tooltip); NB we have
+ // to do it here as the jqm slider sets it every time
+ // the slider's value changes :(
+ this.handle.removeAttr('title');
+
+ newValue = this.element.val();
+
+ font_length = get_value_length( newValue );
+
+ if ( this.popupVisible ) {
+ this.positionPopup();
+
+ switch ( font_length ) {
+ case 1:
+ case 2:
+ font_size = '1.5rem';
+ padding_size = '0.15rem';
+ break;
+ case 3:
+ font_size = '1rem';
+ padding_size = '0.5rem';
+ break;
+ default:
+ font_size = '0.8rem';
+ padding_size = '0.5rem';
+ break;
}
- this.options.running = value;
- this._refresh();
+ this.popup.css({
+ "font-size": font_size,
+ "padding-top": padding_size
+ });
}
- },
- _refresh: function () {
- if ( this.options.running ) {
- this._start();
- } else {
- this._stop();
+ if ( newValue === this.currentValue ) {
+ return;
}
- },
- _create: function () {
- var self = this,
- element = this.element,
- style = element.jqmData( "style" ),
- _html,
- runningClass;
+ switch ( font_length ) {
+ case 1:
+ font_size = '0.95rem';
+ font_top = '0';
+ break;
+ case 2:
+ font_size = '0.85rem';
+ font_top = '-0.01rem';
+ break;
+ case 3:
+ font_size = '0.65rem';
+ font_top = '-0.05rem';
+ break;
+ default:
+ font_size = '0.45rem';
+ font_top = '-0.15rem';
+ break;
+ }
- if ( style ) {
- this.options.style = style;
- } else {
- style = this.options.style;
+ if ( font_size != this.handleText.css('font-size') ) {
+ this.handleText.css({
+ 'font-size': font_size,
+ 'top': font_top
+ });
}
- if ( style == "circle" ) {
- $( this.element ).addClass("ui-progress-container-circle");
+ this.currentValue = newValue;
+ this.handleText.text( newValue );
+ this.popup.html( newValue );
- _html = '<div class="ui-progress-circle"></div>';
- } else if ( style === "pending" ) {
- $( this.element ).addClass("ui-progressbar");
+ this.element.trigger( 'update', newValue );
+ },
- _html = '<div class="ui-progressbar-bg">' +
- '<div class="ui-progress-pending"></div>' +
- '</div>';
+ // show the popup
+ showPopup: function () {
+ if ( !this.options.popup || this.popupVisible ) {
+ return;
}
- this.html = $( _html );
+ this.popup.show();
+ this.popupVisible = true;
+ this._handle_press_show();
+ },
- runningClass = "ui-progress-" + style + "-running";
+ // hide the popup
+ hidePopup: function () {
+ if ( !this.options.popup || !this.popupVisible ) {
+ return;
+ }
- $.extend( this, {
- init: false,
- runningClass: runningClass
- } );
+ this.popup.hide();
+ this.popupVisible = false;
+ this._handle_press_hide();
+ },
- if ( style === "pending" ) {
- $( this.element ).append( this.html );
- this.init = true;
+ _setOption: function (key, value) {
+ var needToChange = ( value !== this.options[key] );
+
+ if ( !needToChange ) {
+ return;
}
- this._refresh();
+ switch ( key ) {
+ case 'popup':
+ this.options.popup = value;
+
+ if ( this.options.popup) {
+ this.updateSlider();
+ } else {
+ this.hidePopup();
+ }
+
+ break;
+ }
}
- } ); /* End of widget */
+ });
+
+ // stop jqm from initialising sliders
+ $( document ).bind( "pagebeforecreate", function ( e ) {
+ if ( $.data( window, "jqmSliderInitSelector" ) === undefined ) {
+ $.data( window, "jqmSliderInitSelector",
+ $.mobile.slider.prototype.options.initSelector );
+ $.mobile.slider.prototype.options.initSelector = null;
+ }
+ });
+ // initialise sliders with our own slider
$( document ).bind( "pagecreate create", function ( e ) {
- $( e.target ).find( ":jqmData(role='progress')" ).progress();
- } );
+ var jqmSliderInitSelector = $.data( window, "jqmSliderInitSelector" );
+ $( e.target ).find(jqmSliderInitSelector).each(function () {
+ var $this = $( this );
+ if ( $this.is("select") ) {
+ $this.slider();
+ } else {
+ $this.tizenslider();
+ }
+ });
+ });
+
}( jQuery, this ));
/*
+ * jQuery Mobile Widget @VERSION
*
* This software is licensed under the MIT licence (as defined by the OSI at
* http://www.opensource.org/licenses/mit-license.php)
- *
+ *
* ***************************************************************************
- * Copyright (C) 2011 by Intel Corporation Ltd.
- *
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2011 by Intel Corporation Ltd.
+ *
* Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software" ),
+ * copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
- *
+ *
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
- *
+ *
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ***************************************************************************
+ *
+ * Authors: Kalyan Kondapally <kalyan.kondapally@intel.com>,
+ * Elliot Smith <elliot.smith@intel.com>
+ * Hyunjung Kim <hjnim.kim@samsung.com>
*/
-// Base class for widgets that need the following features:
-//
-// I. HTML prototype loading
-//
-// This class provides HTML prototype loading for widgets. That is, the widget implementation specifies its HTML portions
-// in one continuous HTML snippet, and it optionally provides an object containing selectors into the various parts of the
-// HTML snippet. This widget loads the HTML snippet into a jQuery object, and optionally assigns jQuery objects to each of
-// the selectors in the optionally provided object.
-//
-// To use this functionality you can either derive from this class, or you can call its prototype's gtype method.
-//
-// 1. Widgets deriving from this class should define _htmlProto as part of their prototype declaration. _htmlProto looks like
-// this:
-//
-// _htmlProto: {
-// source: string|jQuery object (optional) default: string - The name of the widget
-// ui: {
-// uiElement1: "#ui-element-1-selector",
-// uiElement2: "#ui-element-2-selector",
-// ...
-// subElement: {
-// subElement1: "#sub-element-1-selector",
-// subElement2: "#sub-element-2-selector",
-// ...
-// }
-// ...
-// }
-// }
-//
-// If neither 'source' nor 'ui' are defined, you must still include an empty _htmlProto key (_htmlProto: {}) to indicate
-// that you wish to make use of this feature. This will cause a prototype HTML file named after your widget to be loaded.
-// The loaded prototype will be placed into your widget's prototype's _protoHtml.source key.
-//
-// If 'source' is defined as a string, it is the name of the widget (including namespace). This is the default. If your
-// widget's HTML prototype is loaded via AJAX and the name of the AJAX file is different from the name of your widget
-// (that is, it is not "<widgetName>.prototype.html", then you should explicitly define 'source' as:
-//
-// If you wish to load HTML prototypes via AJAX, modify the getProtoPath() function defined below to reflect the directory
-// structure holding your widget HTML prototypes.
-//
-// source: "alternateWidgetName"
-//
-// If AJAX loading fails, source is set to a jQuery object containing a div with an error message. You can check whether
-// loading failed via the jQuery object's jqmData( "tizen.widgetex.ajax.fail" ) data item. If false, then the jQuery object
-// is the actual prototype loaded via AJAX or present inline. Otherwise, the jQuery object is the error message div.
-//
-// If 'source' is defined as a jQuery object, it is considered already loaded.
-//
-// if 'ui' is defined inside _htmlProto, It is assumed to be an object such that every one of its keys is either a string,
-// or another object with the same properties as itself.
-//
-// When a widget is instantiated, the HTML prototype is loaded if not already present in the prototype. If 'ui' is present
-// inside _htmlProto, the prototype is cloned. Then, a new structure is created based on 'ui' with each selector replaced
-// by a jQuery object containing the results of performing .find() on the prototype's clone with the filter set to the
-// value of the string. In the special case where the selector starts with a '#', the ID is removed from the element after
-// it is assigned into the structure being created. This structure is then made accessible from the widget instance via
-// the '_ui' key (i.e., this._ui).
-//
-// 2. Use the loadPrototype method when your widget does not derive from $.tizen.widgetex:
-// Add _htmlProto to your widget's prototype as described above. Then, in your widget's _create() method, call
-// loadPrototype in the following manner:
-//
-// $.tizen.widgetex.loadPrototype.call(this, "namespace.widgetName" );
-//
-// Thereafter, you may use the HTML prototype from your widget's prototype or, if you have specified a 'ui' key in your
-// _htmlProto key, you may use this._ui from your widget instance.
-//
-// II. realize method
-//
-// When a widget is created, some of its properties cannot be set immediately, because they depend on the widths/heights
-// of its constituent elements. They can only be calculated when the page containing the widget is made visible via the
-// "pageshow" event, because widths/heights always evaluate to 0 when retrieved from a widget that is not visible. When
-// you inherit from widgetex, you can add a "_realize" function to your prototype. This function will be called once right
-// after _create() if the element that anchors your widget is on a visible page. Otherwise, it will be called when the
-// page to which the widget belongs emits the "pageshow" event.
-//
-// NB: If your widget is inside a container which is itself not visible, such as an expandable or a collapsible, your
-// widget will remain hidden even though "pageshow" is fired and therefore _realize is called. In this case, widths and
-// heights will be unreliable even during _realize.
-//
-// III. systematic option handling
-//
-// If a widget has lots of options, the _setOption function can become a long switch for setting each recognized option.
-// It is also tempting to allow options to determine the way a widget is created, by basing decisions on various options
-// during _create(). Often, the actions based on option values in _create() are the same as those in _setOption. To avoid
-// such code duplication, this class calls _setOption once for each option after _create() has completed.
-//
-// Furthermore, to avoid writing long switches in a widget's _setOption method, this class implements _setOption in such
-// a way that, for any given option (e.g. "myOption" ), _setOption looks for a method _setMyOption in the widget's
-// implementation, and if found, calls the method with the value of the option.
-//
-// If your widget does not inherit from widgetex, you can still use widgetex' systematic option handling:
-// 1. define the _setOption method for your widget as follows:
-// _setOption: $.tizen.widgetex.prototype._setOption
-// 2. Call this._setOptions(this.options) from your widget's _create() function.
-// 3. As with widgetex-derived widgets, implement a corresponding _setMyOptionName function for each option myOptionName
-// you wish to handle.
-//
-// IV. systematic value handling for input elements
-//
-// If your widget happens to be constructed from an <input> element, you have to handle the "value" attribute specially,
-// and you have to emit the "change" signal whenever it changes, in addition to your widget's normal signals and option
-// changes. With widgetex, you can assign one of your widget's "data-*" properties to be synchronized to the "value"
-// property whenever your widget is constructed onto an <input> element. To do this, define, in your prototype:
-//
-// _value: {
-// attr: "data-my-attribute",
-// signal: "signal-to-emit"
-// }
-//
-// Then, call this._setValue(newValue) whenever you wish to set the value for your widget. This will set the data-*
-// attribute, emit the custom signal (if set) with the new value as its parameter, and, if the widget is based on an
-// <input> element, it will also set the "value" attribute and emit the "change" signal.
+// Widget which turns a html element into a "swipe":
+// i.e. each list item has a sliding "cover" which can be swiped
+// to the right (to reveal buttons underneath) or left (to
+// cover the buttons again). Clicking on a button under a swipe
+// also moves the cover back to the left.
//
-// "attr" is required if you choose to define "_value", and identifies the data-attribute to set in addition to "value",
-// if your widget's element is an input.
-// "signal" is optional, and will be emitted when setting the data-attribute via this._setValue(newValue).
+// In this case, the cover is over a grid of buttons;
+// but it is should also be possible to use other types of markup under the
+// list items.
//
-// If your widget does not derive from widgetex, you can still define "_value" as described above and call
-// $.tizen.widgetex.setValue(widget, newValue).
+// WARNING: This doesn't work well inside a scrollview widget, as
+// the touch events currently interfere with each other badly (e.g.
+// a swipe will work but cause a scroll as well).
//
-// V. Systematic enabled/disabled handling for input elements
+// Theme: default is to use the theme on the target element,
+// theme passed in options, parent theme, or 'c' if none of the above.
+// If list items are themed individually, the cover will pick up the
+// theme of the list item which is its parent.
//
-// widgetex implements _setDisabled which will disable the input associated with this widget, if any. Thus, if you derive
-// from widgetex and you plan on implementing the disabled state, you should chain up to
-// $.tizen.widgetex.prototype._setDisabled(value), rather than $.Widget.prototype._setOption( "disabled", value).
-
-(function ($, undefined) {
-
-// Framework-specific HTML prototype path for AJAX loads
- function getProtoPath() {
- var theScriptTag = $( "script[data-framework-version][data-framework-root][data-framework-theme]" );
-
- return (theScriptTag.attr( "data-framework-root" ) + "/" +
- theScriptTag.attr( "data-framework-version" ) + "/themes/" +
- theScriptTag.attr( "data-framework-theme" ) + "/proto-html" );
- }
-
- $.widget( "tizen.widgetex", $.mobile.widget, {
- _createWidget: function () {
- $.tizen.widgetex.loadPrototype.call( this, this.namespace + "." + this.widgetName );
- $.mobile.widget.prototype._createWidget.apply( this, arguments );
- },
-
- _init: function () {
- // TODO THIS IS TEMPORARY PATCH TO AVOID CTXPOPUP PAGE CRASH
- if ( this.element === undefined ) {
- return;
- }
-
- var page = this.element.closest( ".ui-page" ),
- self = this,
- myOptions = {};
-
- if ( page.is( ":visible" ) ) {
- this._realize();
- } else {
- page.bind( "pageshow", function () { self._realize(); } );
- }
- $.extend( myOptions, this.options );
-
- this.options = {};
+/**
+ @class Swipe
+ The swipe widget shows a view on the screen where the items can be swiped vertically to show a menu.
+ To add a swipe widget to the application, use the following code:
- this._setOptions( myOptions );
- },
+ <ul data-role="listview">
+ <li data-role="swipe">
+ <div data-role="swipe-cover">
+ <div data-role="button" data-inline="true">OK</div>
+ <div data-role="button" data-inline="true">Cancel</div>
+ </div>
+ <div data-role="swipe-item-cover">
+ <p>This is a swipe item cover.<br>
+ This will be swiped out when swipe event comes.</p>
+ </div>
+ </li>
+ </ul>
- _getCreateOptions: function () {
- // if we're dealing with an <input> element, value takes precedence over corresponding data-* attribute, if a
- // mapping has been established via this._value. So, assign the value to the data-* attribute, so that it may
- // then be assigned to this.options in the superclass' _getCreateOptions
+ You can use methods with the swipe as described in the jQueryMobile documentation for view methods.
+*/
+/**
+ @property {String} data-role
+ Creates a swipe using the HTML unordered view (>ul<) element.
+ The default value is swipe.
- if (this.element.is( "input" ) && this._value !== undefined) {
- var theValue =
- ( ( this.element.attr( "type" ) === "checkbox" || this.element.attr( "type" ) === "radio" )
- ? this.element.is( ":checked" )
- : this.element.is( "[value]" )
- ? this.element.attr( "value" )
- : undefined);
+ Creates a swipe item cover using an HTML $gt;div$lt; element. This cover can be swiped to show the content beneath it.
+ The default value is swipe-item-cover.
+*/
+/**
+ @method open
+ uncover swipe item
+*/
+/**
+ @method close
+ cover swipe item
+*/
+/**
+ @method opened
+ return coveritem status( coverd or uncovred )
+*/
+/**
+ @event animationstart
+ The swipe can define a callback for the animationstart event, which is fired after a item is swipe and the swipe animation is start:
+*/
+/**
+ @event animationend
+ The swipe can define a callback for the animationend event, which is fired after a item is swiped and the swipe animation is complete:
- if ( theValue != undefined ) {
- this.element.attr( this._value.attr, theValue );
- }
- }
+ <ul data-role="listview">
+ <li data-role="swipe">
+ <div data-role="swipe-cover">
+ <div data-role="button" data-inline="true">OK</div>
+ <div data-role="button" data-inline="true">Cancel</div>
+ </div>
+ <div data-role="swipe-item-cover" id="foo">
+ <p>This is a swipe item cover.<br>
+ This will be swiped out when swipe event comes.</p>
+ </div>
+ </li>
+ </ul>
+ $("#foo").bind("animationend", function (ev)
+ {
+ Console.log("Swipe cover's animation is complete.");
+ });
+*/
+(function ($) {
- return $.mobile.widget.prototype._getCreateOptions.apply( this, arguments );
+ $.widget("tizen.swipe", $.mobile.widget, {
+ options: {
+ theme: null
},
- _setOption: function ( key, value ) {
- var setter = "_set" + key.replace(/^[a-z]/, function (c) { return c.toUpperCase(); } );
-
- if ( this[setter] !== undefined ) {
- this[setter]( value );
- } else {
- $.mobile.widget.prototype._setOption.apply( this, arguments );
- }
- },
+ _create: function () {
+ // use the theme set on the element, set in options,
+ // the parent theme, or 'c' (in that order of preference)
+ var theme = this.element.jqmData('theme') ||
+ this.options.theme ||
+ this.element.parent().jqmData('theme') ||
+ 's';
- _setDisabled: function ( value ) {
- $.Widget.prototype._setOption.call( this, "disabled", value );
- if ( this.element.is( "input" ) ) {
- this.element.attr( "disabled", value );
- }
+ this.options.theme = theme;
+ this._isopen = false;
+ this.refresh();
},
- _setValue: function ( newValue ) {
- $.tizen.widgetex.setValue( this, newValue );
- },
+ refresh: function () {
+ this._cleanupDom();
- _realize: function () {}
- } );
+ var self = this,
+ defaultCoverTheme,
+ covers,
+ coverTheme,
+ item,
+ itemHasThemeClass;
- $.tizen.widgetex.setValue = function ( widget, newValue ) {
- if ( widget._value !== undefined ) {
- var valueString = ( widget._value.makeString ? widget._value.makeString(newValue) : newValue ),
- inputType;
+ defaultCoverTheme = 'ui-body-' + this.options.theme;
- widget.element.attr( widget._value.attr, valueString );
- if ( widget._value.signal !== undefined ) {
- widget.element.triggerHandler( widget._value.signal, newValue );
+ if ( !this.element.parent().hasClass('ui-listview') ) {
+ this.element.parent().listview();
}
+ this.element.addClass('ui-swipe');
- if ( widget.element.is( "input" ) ) {
- inputType = widget.element.attr( "type" );
-
- // Special handling for checkboxes and radio buttons, where the presence of the "checked" attribute is really
- // the value
- if ( inputType === "checkbox" || inputType === "radio" ) {
- if ( newValue ) {
- widget.element.attr( "checked", true );
- } else {
- widget.element.removeAttr( "checked" );
- }
- } else {
- widget.element.attr( "value", valueString );
- }
+ // get the item covers
+ covers = this.element.find(':jqmData(role="swipe-item-cover")');
+ item = this.element.find(':jqmData(role="swipe-item")');
- widget.element.trigger( "change" );
- }
- }
- };
+ this._covers = covers;
+ this._item = item;
+ item.addClass('ui-swipe-item');
+ coverTheme = defaultCoverTheme;
+ itemHasThemeClass = item.parent().attr('class')
+ .match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/);
- $.tizen.widgetex.assignElements = function (proto, obj) {
- var ret = {},
- key;
+ covers.each( function () {
+ var cover = $( this );
- for ( key in obj ) {
- if ( ( typeof obj[key] ) === "string" ) {
- ret[key] = proto.find( obj[key] );
- if ( obj[key].match(/^#/) ) {
- ret[key].removeAttr( "id" );
- }
- } else {
- if ( (typeof obj[key]) === "object" ) {
- ret[key] = $.tizen.widgetex.assignElements( proto, obj[key] );
+ if ( itemHasThemeClass ) {
+ coverTheme = itemHasThemeClass[0];
}
- }
- }
-
- return ret;
- };
-
- $.tizen.widgetex.loadPrototype = function ( widget, ui ) {
- var ar = widget.split( "." ),
- namespace,
- widgetName,
- source,
- noSource = false,
- htmlProto,
- protoPath;
- if ( ar.length == 2 ) {
- namespace = ar[0];
- widgetName = ar[1];
+ cover.addClass('ui-swipe-item-cover');
+ cover.addClass( coverTheme );
- // If htmlProto is defined
- if ( $[namespace][widgetName].prototype._htmlProto !== undefined ) {
- // If no source is defined, use the widget name
- source = $[namespace][widgetName].prototype._htmlProto.source;
- if ( source === undefined ) {
- source = widgetName;
- noSource = true;
+ if ( cover.has('.ui-swipe-item-cover-inner').length === 0 ) {
+ cover.wrapInner( $('<span/>').addClass('ui-swipe-item-cover-inner') );
}
- // Load the HTML prototype via AJAX if not defined inline
- if ( typeof source === "string" ) {
- if ( noSource ) { // use external htmlproto file
- // Establish the path for the proto file
- widget = source;
- protoPath = getProtoPath();
-
- // Make the AJAX call
- $.ajax( {
- url: protoPath + "/" + widget + ".prototype.html",
- async: false,
- dataType: "html"
- }).success( function (data, textStatus, jqXHR ) {
- source = $( "<div></div>" ).html(data).jqmData( "tizen.widgetex.ajax.fail", false );
- } );
-
- // Assign the HTML proto to the widget prototype
- source = $( "<div></div>" )
- .text( "Failed to load proto for widget " + namespace + "." + widgetName + "!" )
- .css( {background: "red", color: "blue", border: "1px solid black"} )
- .jqmData( "tizen.widgetex.ajax.fail", true );
-
- } else {
- // inline definition (string)
- source = $( source ).jqmData( "tizen.widgetex.ajax.fail", false );
- }
-
- } else {
- // inline definition (object)
- // AJAX loading has trivially succeeded, since there was no AJAX loading at all
- source.jqmData( "tizen.widgetex.ajax.fail", false );
- }
- htmlProto = source;
- $[namespace][widgetName].prototype._htmlProto.source = source;
+ if ( !( cover.data('animateRight') && cover.data('animateLeft') ) ) {
+ cover.data('animateRight', function () {
+ self._animateCover( cover, 110, item );
+ });
- // If there's a "ui" portion in the HTML proto, copy it over to this instance, and
- // replace the selectors with the selected elements from a copy of the HTML prototype
- if ( $[namespace][widgetName].prototype._htmlProto.ui !== undefined ) {
- // Assign the relevant parts of the proto
- $.extend( this, {
- _ui: $.tizen.widgetex.assignElements( htmlProto.clone(), $[namespace][widgetName].prototype._htmlProto.ui )
+ cover.data('animateLeft', function () {
+ self._animateCover( cover, 0, item );
});
}
- }
- }
- };
-
-}( jQuery ) );
+ // bind to synthetic events
+ item.bind( 'swipeleft', cover.data('animateLeft') );
+ cover.bind( 'swiperight', cover.data('animateRight') );
+ item.find( '.ui-btn' ).bind( 'vclick', cover.data('animateLeft') );
+ } );
+ },
-/*
- * jQuery UI Progressbar @VERSION
- *
- * Copyright 2011, AUTHORS.txt (http://jqueryui.com/about)
- * Dual licensed under the MIT or GPL Version 2 licenses.
- * http://jquery.org/license
- *
- * http://docs.jquery.com/UI/Progressbar
- *
- * Depends:
- * jquery.ui.core.js
- * jquery.ui.widget.js
- * Original file:
- * jquery.ui.progressbar.js
- */
-/* This is from jquery ui plugin - progressbar 11/16/2011 */
+ _cleanupDom: function () {
+ var self = this,
+ defaultCoverTheme,
+ cover,
+ coverTheme = defaultCoverTheme,
+ item,
+ itemClass,
+ itemHasThemeClass,
+ text,
+ wrapper;
+ defaultCoverTheme = 'ui-body-' + this.options.theme;
-/**
- @class ProgressBar
- The progress bar widget shows a control that indicates the progress percentage of an on-going operation. This widget can be scaled to fit inside a parent container.
+ this.element.removeClass('ui-swipe');
- To add a progress bar widget to the application, use the following code:
+ // get the item covers
+ cover = this.element.find(':jqmData(role="swipe-item-cover")');
+ item = this.element.find(':jqmData(role="swipe-item")');
- <div id="foo" data-role="progressbar"</div>
-*/
-/**
- @event change
- The progress bar can define a callback for the change event, which is fired when the progress value is changed:
- <div id="foo" data-role="progressbar"></div>
- $("#foo").bind("change", function (ev, val) {
- Console.log("Value is changed to " + val);
- });
-*/
-/**
- @method value
- You can use the value method with the pickers to set or get the current default progress bar value:
+ item.removeClass('ui-swipe-item');
+ cover.removeClass('ui-swipe-item-cover');
- <div id="foo" data-role="progressbar"></div>
- var oldVal = $("#foo").progressbar("value");
- $("#foo").progressbar("value", 50);
-*/
+ itemClass = item.attr('class');
+ itemHasThemeClass = itemClass &&
+ itemClass.match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/);
-(function ( $, window, undefined ) {
+ if ( itemHasThemeClass ) {
+ coverTheme = itemHasThemeClass[0];
+ }
- $.widget( "tizen.progressbar", $.mobile.widget, {
- options: {
- value: 0,
- max: 100
- },
+ cover.removeClass(coverTheme);
- min: 0,
+ // remove wrapper HTML
+ wrapper = cover.find('.ui-swipe-item-cover-inner');
+ wrapper.children().unwrap();
+ text = wrapper.text();
- _create: function () {
- this.element
- .addClass( "ui-progressbar" )
- .attr( {
- role: "progressbar",
- "aria-valuemin": this.min,
- "aria-valuemax": this.options.max,
- "aria-valuenow": this._value()
- } );
+ if ( text ) {
+ cover.append( text );
+ wrapper.remove();
+ }
- this.valueDiv = $( "<div class='ui-progressbar-value'></div>" )
- .appendTo( this.element );
+ // unbind swipe events
+ if ( cover.data('animateRight') && cover.data('animateLeft') ) {
+ cover.unbind( 'swiperight', cover.data('animateRight') );
+ item.unbind( 'swipeleft', cover.data('animateLeft') );
- this.valueDiv.wrap("<div class='ui-progressbar-bg'></div>");
+ // unbind clicks on buttons inside the item
+ item.find('.ui-btn').unbind( 'vclick', cover.data('animateLeft') );
- this.oldValue = this._value();
- this._refreshValue();
+ cover.data( 'animateRight', null );
+ cover.data( 'animateLeft', null );
+ }
},
- _destroy: function () {
- this.element
- .removeClass( "ui-progressbar" )
- .removeAttr( "role" )
- .removeAttr( "aria-valuemin" )
- .removeAttr( "aria-valuemax" )
- .removeAttr( "aria-valuenow" );
+ // NB I tried to use CSS animations for this, but the performance
+ // and appearance was terrible on Android 2.2 browser;
+ // so I reverted to jQuery animations
+ //
+ // once the cover animation is done, the cover emits an
+ // animationComplete event
+ _animateCover: function ( cover, leftPercentage, item ) {
+ var self = this,
+ animationOptions = {
+ easing: 'linear',
+ duration: 'normal',
+ queue: true,
+ complete: function () {
+ cover.trigger('animationend');
+ }
+ };
- this.valueDiv.remove();
- },
+ $( this.element.parent() )
+ .find(":jqmData(role='swipe')")
+ .each(
+ function () {
+ if ( this !== self.element.get(0) &&
+ $( this ).swipe("opened") ) {
+ $( this ).swipe("close");
+ }
+ }
+ );
- value: function ( newValue ) {
- if ( newValue === undefined ) {
- return this._value();
+ if ( leftPercentage == 110 ) {
+ this._isopen = true;
+ } else {
+ this._isopen = false;
}
- this._setOption( "value", newValue );
- return this;
- },
-
- _setOption: function ( key, value ) {
- if ( key === "value" ) {
- this.options.value = value;
- this._refreshValue();
- if ( this._value() === this.options.max ) {
- this.element.trigger( "complete" );
- }
+ cover.stop();
+ cover.clearQueue();
+ cover.trigger('animationstart');
+ cover.animate( { left: leftPercentage + '%' }, animationOptions );
+ if ( leftPercentage == 0 ) {
+ item.animate({ opacity: 0 }, "slow");
+ } else {
+ item.animate({ opacity: 1 }, "slow");
}
- // jquery.ui.widget.js MUST be updated to new version!
- //this._super( "_setOption", key, value );
+
},
- _value: function () {
- var val = this.options.value;
- // normalize invalid value
- if ( typeof val !== "number" ) {
- val = 0;
- }
- return Math.min( this.options.max, Math.max( this.min, val ) );
+ destroy: function () {
+ this._cleanupDom();
},
- _percentage: function () {
- return 100 * this._value() / this.options.max;
+ open: function () {
+ var self = this;
+
+ $( self._covers ).each( function () {
+ var cover = $( this );
+ self._animateCover( cover, 110, self._item);
+ } );
},
- _refreshValue: function () {
- var value = this.value(),
- percentage = this._percentage();
+ opened: function () {
+ return this._isopen;
+ },
- if ( this.oldValue !== value ) {
- this.oldValue = value;
- this.element.trigger( "change" );
- }
+ close: function () {
+ var self = this;
- this.valueDiv
- .toggle( value > this.min )
- .width( percentage.toFixed(0) + "%" );
- this.element.attr( "aria-valuenow", value );
+ $( self._covers ).each( function () {
+ var cover = $( this );
+ self._animateCover( cover, 0, self._item);
+ } );
}
- } );
- // auto self-init widgets
- $( document ).bind( "pagecreate", function ( e ) {
- $( e.target ).find( ":jqmData(role='progressbar')" ).progressbar();
- } );
+ });
-}( jQuery, this ) );
+ $( document ).bind("pagecreate", function ( e ) {
+ $( e.target ).find(":jqmData(role='swipe')").swipe();
+ });
+}( jQuery ));
-/*
- * jQuery Mobile Widget @VERSION
- *
- * This software is licensed under the MIT licence (as defined by the OSI at
- * http://www.opensource.org/licenses/mit-license.php)
- *
- * ***************************************************************************
+
+/* ***************************************************************************
* Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- * Copyright (c) 2011 by Intel Corporation Ltd.
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* DEALINGS IN THE SOFTWARE.
* ***************************************************************************
*
- * Authors: Kalyan Kondapally <kalyan.kondapally@intel.com>,
- * Elliot Smith <elliot.smith@intel.com>
- * Hyunjung Kim <hjnim.kim@samsung.com>
+ * Author: Minkyu Kang <mk7.kang@samsung.com>
*/
-// Widget which turns a html element into a "swipe":
-// i.e. each list item has a sliding "cover" which can be swiped
-// to the right (to reveal buttons underneath) or left (to
-// cover the buttons again). Clicking on a button under a swipe
-// also moves the cover back to the left.
-//
-// In this case, the cover is over a grid of buttons;
-// but it is should also be possible to use other types of markup under the
-// list items.
-//
-// WARNING: This doesn't work well inside a scrollview widget, as
-// the touch events currently interfere with each other badly (e.g.
-// a swipe will work but cause a scroll as well).
-//
-// Theme: default is to use the theme on the target element,
-// theme passed in options, parent theme, or 'c' if none of the above.
-// If list items are themed individually, the cover will pick up the
-// theme of the list item which is its parent.
-//
+/*
+ * Notification widget
+ *
+ * HTML Attributes
+ *
+ * data-role: set to 'notification'.
+ * data-type: 'ticker' or 'popup'.
+ * data-interval: time to showing. If don't set, will show infinitely.
+ *
+ * APIs
+ *
+ * open(): open the notification.
+ * close(): close the notification.
+ * text(text0, text1): set texts or get texts
+ * icon(src): set the icon (tickernoti only)
+ *
+ * Events
+ *
+ * N/A
+ *
+ * Examples
+ *
+ * // tickernoti
+ * <div data-role="notification" id="notification" data-type="ticker" data-interval="3000">
+ * <img src="icon01.png">
+ * <p>Hello World</p>
+ * <p>Denis</p>
+ * </div>
+ *
+ * // smallpopup
+ * <div data-role="notification" id="notification" data-type="popup" data-interval="3000">
+ * <p>Hello World</p>
+ * </div>
+ *
+ */
/**
- @class Swipe
- The swipe widget shows a view on the screen where the items can be swiped vertically to show a menu.
- To add a swipe widget to the application, use the following code:
-
- <ul data-role="listview">
- <li data-role="swipe">
- <div data-role="swipe-cover">
- <div data-role="button" data-inline="true">OK</div>
- <div data-role="button" data-inline="true">Cancel</div>
- </div>
- <div data-role="swipe-item-cover">
- <p>This is a swipe item cover.<br>
- This will be swiped out when swipe event comes.</p>
- </div>
- </li>
- </ul>
+ @class Notification
+ The notification widget shows a pop-up window on the screen to provide notifications.
+ To add a notification widget to the application, use the following code:
- You can use methods with the swipe as described in the jQueryMobile documentation for view methods.
+ <div data-role="page">
+ <div data-role="notification" data-type="smallpopup">
+ <p>text1</p>
+ </div>
+ <div data-role="header"></div>
+ <div data-role="content"></div>
+ <div data-role="footer"></div>
+ </div>
*/
/**
- @property {String} data-role
- Creates a swipe using the HTML unordered view (>ul<) element.
- The default value is swipe.
+ @property {String} data-type
+ Defines the notification type. The type options are tickernoti and smallpopup. <br/>The default value is smallpopup.
- Creates a swipe item cover using an HTML $gt;div$lt; element. This cover can be swiped to show the content beneath it.
- The default value is swipe-item-cover.
*/
/**
- @method open
- uncover swipe item
+ @property {Integer} data-interval
+ Defines the time to showing a notification widget. <br/>The default is infinitely.
+
*/
/**
- @method close
- cover swipe item
+ @method open
+ The open method is used to open the notification widget:
+
+ <div data-role="notification" data-type="smallpopup" data-interval="3000"></div>
+ $('#notification').notification('open');
*/
/**
- @method opened
- return coveritem status( coverd or uncovred )
+ @method close
+ The close method is used to close the notification widget:
+
+ <div data-role="notification" data-type="smallpopup" data-interval="3000"></div>
+ $('#notification').notification('close');
*/
/**
- @event animationstart
- The swipe can define a callback for the animationstart event, which is fired after a item is swipe and the swipe animation is start:
+ @method text
+ The text method is used to set or get the notification text:
+
+ <div data-role="notification" data-type="smallpopup" data-interval="3000"></div>
+ // Set notification text
+ $('#notification').notification('text', 'setThisText');
+ // Get notification text
+ texts = $('#notification').notification('text');
+ @since Tizen2.0
*/
/**
- @event animationend
- The swipe can define a callback for the animationend event, which is fired after a item is swiped and the swipe animation is complete:
+ @method icon
+ The setIcon method is used to set the ticker notification icon. The icon can be set only if the notification type is set to tickernoti.
- <ul data-role="listview">
- <li data-role="swipe">
- <div data-role="swipe-cover">
- <div data-role="button" data-inline="true">OK</div>
- <div data-role="button" data-inline="true">Cancel</div>
- </div>
- <div data-role="swipe-item-cover" id="foo">
- <p>This is a swipe item cover.<br>
- This will be swiped out when swipe event comes.</p>
- </div>
- </li>
- </ul>
- $("#foo").bind("animationend", function (ev)
- {
- Console.log("Swipe cover's animation is complete.");
- });
+ <div data-role="notification" data-type="ticker" data-interval="3000"></div>
+ $('#notification').notification('icon', './test.png');
*/
-(function ($) {
+(function ( $, window ) {
+ $.widget( "tizen.notification", $.mobile.widget, {
+ btn: null,
+ text_bg: [],
+ icon_img: [],
+ interval: null,
+ seconds: null,
+ running: false,
- $.widget("tizen.swipe", $.mobile.widget, {
- options: {
- theme: null
+ _get_text: function () {
+ var text = new Array( 2 );
+
+ if ( this.type === 'ticker' ) {
+ text[0] = $( this.text_bg[0] ).text();
+ text[1] = $( this.text_bg[1] ).text();
+ } else {
+ text[0] = $( this.text_bg[0] ).text();
+ }
+
+ return text;
},
- _create: function () {
- // use the theme set on the element, set in options,
- // the parent theme, or 'c' (in that order of preference)
- var theme = this.element.jqmData('theme') ||
- this.options.theme ||
- this.element.parent().jqmData('theme') ||
- 's';
+ _set_text: function ( text0, text1 ) {
+ var _set = function ( elem, text ) {
+ if ( !text ) {
+ return;
+ }
+ elem.text( text );
+ };
- this.options.theme = theme;
- this._isopen = false;
- this.refresh();
+ if ( this.type === 'ticker' ) {
+ _set( $( this.text_bg[0] ), text0 );
+ _set( $( this.text_bg[1] ), text1 );
+ } else {
+ _set( $( this.text_bg[0] ), text0 );
+ }
},
- refresh: function () {
- this._cleanupDom();
+ text: function ( text0, text1 ) {
+ if ( text0 === undefined && text1 === undefined ) {
+ return this._get_text();
+ }
- var self = this,
- defaultCoverTheme,
- covers,
- coverTheme,
- item,
- itemHasThemeClass;
+ this._set_text( text0, text1 );
+ },
- defaultCoverTheme = 'ui-body-' + this.options.theme;
+ icon: function ( src ) {
+ if ( src === undefined ) {
+ return;
+ }
- if ( !this.element.parent().hasClass('ui-listview') ) {
- this.element.parent().listview();
+ this.icon_img.detach();
+ this.icon_img = $( "<img src='" + src + "' class='ui-ticker-icon'>" );
+ $( this.element ).find(".ui-ticker").append( this.icon_img );
+ },
+
+ _refresh: function () {
+ var container = this._get_container();
+
+ $( container ).addClass("fix")
+ .removeClass("show")
+ .removeClass("hide");
+
+ this._set_interval();
+ },
+
+ open: function () {
+ var container = this._get_container();
+
+ if ( this.running ) {
+ this._refresh();
+ return;
}
- this.element.addClass('ui-swipe');
- // get the item covers
- covers = this.element.find(':jqmData(role="swipe-item-cover")');
- item = this.element.find(':jqmData(role="swipe-item")');
+ $( container ).addClass("show")
+ .removeClass("hide")
+ .removeClass("fix");
- this._covers = covers;
- this._item = item;
- item.addClass('ui-swipe-item');
- coverTheme = defaultCoverTheme;
- itemHasThemeClass = item.parent().attr('class')
- .match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/);
+ this.running = true;
- covers.each( function () {
- var cover = $( this );
+ if ( this.type === 'popup' ) {
+ this._set_position();
+ }
- if ( itemHasThemeClass ) {
- coverTheme = itemHasThemeClass[0];
- }
+ this._set_interval();
+ },
- cover.addClass('ui-swipe-item-cover');
- cover.addClass( coverTheme );
+ close: function () {
+ var container = this._get_container();
- if ( cover.has('.ui-swipe-item-cover-inner').length === 0 ) {
- cover.wrapInner( $('<span/>').addClass('ui-swipe-item-cover-inner') );
- }
+ if ( !this.running ) {
+ return;
+ }
- if ( !( cover.data('animateRight') && cover.data('animateLeft') ) ) {
- cover.data('animateRight', function () {
- self._animateCover( cover, 110, item );
- });
+ $( container ).addClass("hide")
+ .removeClass("show")
+ .removeClass("fix");
- cover.data('animateLeft', function () {
- self._animateCover( cover, 0, item );
- });
- }
+ this.running = false;
+ clearInterval( this.interval );
+ },
- // bind to synthetic events
- item.bind( 'swipeleft', cover.data('animateLeft') );
- cover.bind( 'swiperight', cover.data('animateRight') );
- item.find( '.ui-btn' ).bind( 'vclick', cover.data('animateLeft') );
- } );
+ destroy: function () {
+ var container = this._get_container();
+ $( container ).removeClass("show")
+ .removeClass("hide")
+ .removeClass("fix");
+
+ this._del_event();
+
+ this.running = false;
},
- _cleanupDom: function () {
+ _get_container: function () {
+ if ( this.type === 'ticker' ) {
+ return $( this.element ).find(".ui-ticker");
+ }
+
+ return $( this.element ).find(".ui-smallpopup");
+ },
+
+ _set_interval: function () {
+ var self = this;
+
+ clearInterval( this.interval );
+
+ if ( this.seconds !== undefined && this.second !== 0 ) {
+ this.interval = setInterval( function () {
+ self.close();
+ }, this.seconds );
+ }
+ },
+
+ _add_event: function () {
var self = this,
- defaultCoverTheme,
- cover,
- coverTheme = defaultCoverTheme,
- item,
- itemClass,
- itemHasThemeClass,
- text,
- wrapper;
+ container = this._get_container();
- defaultCoverTheme = 'ui-body-' + this.options.theme;
+ if ( this.type === 'ticker' ) {
+ container.find(".ui-ticker-btn").append( this.btn ).trigger("create");
- this.element.removeClass('ui-swipe');
+ this.btn.bind( "vmouseup", function () {
+ self.close();
+ });
+ }
- // get the item covers
- cover = this.element.find(':jqmData(role="swipe-item-cover")');
- item = this.element.find(':jqmData(role="swipe-item")');
+ container.bind( 'vmouseup', function () {
+ self.close();
+ });
+ },
- item.removeClass('ui-swipe-item');
- cover.removeClass('ui-swipe-item-cover');
+ _del_event: function () {
+ var container = this._get_container();
+
+ if ( this.type === 'ticker' ) {
+ this.btn.unbind("vmouseup");
+ }
+ container.unbind('vmouseup');
+ clearInterval( this.interval );
+ },
+
+ _set_position: function () {
+ var container = this._get_container(),
+ $footer = $('.ui-page-active').children('.ui-footer'),
+ footer_h = $footer.outerHeight() || 0;
+
+ container.css( 'bottom', footer_h);
+ },
- itemClass = item.attr('class');
- itemHasThemeClass = itemClass &&
- itemClass.match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/);
+ _create: function () {
+ var self = this,
+ elem = $( this.element ),
+ i;
- if ( itemHasThemeClass ) {
- coverTheme = itemHasThemeClass[0];
- }
+ this.btn = $('<div data-role="button" data-inline="true">Close</div>');
- cover.removeClass(coverTheme);
+ this.seconds = elem.jqmData('interval');
+ this.type = elem.jqmData('type') || 'popup';
- // remove wrapper HTML
- wrapper = cover.find('.ui-swipe-item-cover-inner');
- wrapper.children().unwrap();
- text = wrapper.text();
+ if ( this.type === 'ticker' ) {
+ elem.wrapInner("<div class='ui-ticker'></div>");
+ elem.find(".ui-ticker").append("<div class='ui-ticker-body'></div>" +
+ "<div class='ui-ticker-btn'></div>");
+ this.text_bg = elem.find("p");
- if ( text ) {
- cover.append( text );
- wrapper.remove();
- }
+ if ( this.text_bg.length < 2 ) {
+ elem.find(".ui-ticker").append("<p></p><p></p>");
+ this.text_bg = elem.find("p");
+ } else if ( this.text_bg.length > 2 ) {
+ for ( i = 2; i < this.text_bg.length; i++ ) {
+ $( this.text_bg[i] ).css( "display", "none" );
+ }
+ }
- // unbind swipe events
- if ( cover.data('animateRight') && cover.data('animateLeft') ) {
- cover.unbind( 'swiperight', cover.data('animateRight') );
- item.unbind( 'swipeleft', cover.data('animateLeft') );
+ $( this.text_bg[0] ).addClass("ui-ticker-text1-bg");
+ $( this.text_bg[1] ).addClass("ui-ticker-text2-bg");
- // unbind clicks on buttons inside the item
- item.find('.ui-btn').unbind( 'vclick', cover.data('animateLeft') );
+ this.icon_img = elem.find("img");
- cover.data( 'animateRight', null );
- cover.data( 'animateLeft', null );
- }
- },
+ if ( this.icon_img.length ) {
+ $( this.icon_img ).addClass("ui-ticker-icon");
- // NB I tried to use CSS animations for this, but the performance
- // and appearance was terrible on Android 2.2 browser;
- // so I reverted to jQuery animations
- //
- // once the cover animation is done, the cover emits an
- // animationComplete event
- _animateCover: function ( cover, leftPercentage, item ) {
- var self = this,
- animationOptions = {
- easing: 'linear',
- duration: 'normal',
- queue: true,
- complete: function () {
- cover.trigger('animationend');
+ for ( i = 1; i < this.icon_img.length; i++ ) {
+ $( this.icon_img[i] ).css( "display", "none" );
}
- };
+ }
+ } else {
+ elem.wrapInner("<div class='ui-smallpopup'></div>");
+ this.text_bg = elem.find("p").addClass("ui-smallpopup-text-bg");
- $( this.element.parent() )
- .find(":jqmData(role='swipe')")
- .each(
- function () {
- if ( this !== self.element.get(0) &&
- $( this ).swipe("opened") ) {
- $( this ).swipe("close");
- }
+ if ( this.text_bg.length < 1 ) {
+ elem.find(".ui-smallpopup")
+ .append("<p class='ui-smallpopup-text-bg'></p>");
+ this.text_bg = elem.find("p");
+ } else if ( this.text_bg.length > 1 ) {
+ for ( i = 1; i < this.text_bg.length; i++ ) {
+ $( this.text_bg[i] ).css( "display", "none" );
}
- );
+ }
- if ( leftPercentage == 110 ) {
- this._isopen = true;
- } else {
- this._isopen = false;
+ this._set_position();
}
- cover.stop();
- cover.clearQueue();
- cover.trigger('animationstart');
- cover.animate( { left: leftPercentage + '%' }, animationOptions );
- if ( leftPercentage == 0 ) {
- item.animate({ opacity: 0 }, "slow");
- } else {
- item.animate({ opacity: 1 }, "slow");
- }
+ this._add_event();
- },
+ $( window ).bind( "resize", function () {
+ if ( !self.running ) {
+ return;
+ }
- destroy: function () {
- this._cleanupDom();
- },
+ self._refresh();
- open: function () {
- var self = this;
+ if ( self.type === 'popup' ) {
+ self._set_position();
+ }
+ });
+ }
+ }); // End of widget
- $( self._covers ).each( function () {
- var cover = $( this );
- self._animateCover( cover, 110, self._item);
- } );
- },
+ // auto self-init widgets
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $( e.target ).find(":jqmData(role='notification')").notification();
+ });
- opened: function () {
- return this._isopen;
- },
+ $( document ).bind( "pagebeforehide", function ( e ) {
+ $( e.target ).find(":jqmData(role='notification')").notification('destroy');
+ });
+}( jQuery, this ));
- close: function () {
- var self = this;
- $( self._covers ).each( function () {
- var cover = $( this );
- self._animateCover( cover, 0, self._item);
- } );
- }
- });
+/*
+ * jQuery Mobile Widget @VERSION
+ *
+ * This software is licensed under the MIT licence (as defined by the OSI at
+ * http://www.opensource.org/licenses/mit-license.php)
+ *
+ * ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2011 by Intel Corporation Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * Authors: Gabriel Schulhof <gabriel.schulhof@intel.com>,
+ * Elliot Smith <elliot.smith@intel.com>
+ * Hyunjung Kim <hjnim.kim@samsung.com>
+ */
- $( document ).bind("pagecreate", function ( e ) {
- $( e.target ).find(":jqmData(role='swipe')").swipe();
- });
+/*
+ * % Popupwindow widget do not use anymore(will be deprecated, internal use only)
+ *
+ *
+ * Shows other elements inside a popup window.
+ *
+ * To apply, add the attribute data-role="popupwindow" to a <div> element inside
+ * a page. Alternatively, call popupwindow()
+ * on an element, eg :
+ *
+ * $("#mypopupwindowContent").popupwindow();
+ * where the html might be :
+ * <div id="mypopupwindowContent"></div>
+ *
+ * To trigger the popupwindow to appear, it is necessary to make a call to its
+ * 'open()' method. This is typically done by binding a function to an event
+ * emitted by an input element, such as a the clicked event emitted by a button
+ * element. The open() method takes two arguments, specifying the x and y
+ * screen coordinates of the center of the popup window.
-}( jQuery ));
+ * You can associate a button with a popup window like this:
+ * <div id="mypopupContent" style="display: table;" data-role="popupwindow">
+ * <table>
+ * <tr> <td>Eenie</td> <td>Meenie</td> <td>Mynie</td> <td>Mo</td> </tr>
+ * <tr> <td>Catch-a</td> <td>Tiger</td> <td>By-the</td> <td>Toe</td> </tr>
+ * <tr> <td>If-he</td> <td>Hollers</td> <td>Let-him</td> <td>Go</td> </tr>
+ * <tr> <td>Eenie</td> <td>Meenie</td> <td>Mynie</td> <td>Mo</td> </tr>
+ * </table>
+ * </div>
+ * <a href="#myPopupContent" data-rel="popupwindow" data-role="button">Show popup</a>
+ *
+ * Options:
+ *
+ * theme: String; the theme for the popupwindow contents
+ * Default: null
+ *
+ * overlayTheme: String; the theme for the popupwindow
+ * Default: null
+ *
+ * shadow: Boolean; display a shadow around the popupwindow
+ * Default: true
+ *
+ * corners: Boolean; display a shadow around the popupwindow
+ * Default: true
+ *
+ * fade: Boolean; fades the opening and closing of the popupwindow
+ *
+ * transition: String; the transition to use when opening or closing
+ * a popupwindow
+ * Default: $.mobile.defaultDialogTransition
+ *
+ * Events:
+ * popupbeforeposition: triggered after a popup has completed preparations for opening, but has not yet opened
+ * popupafteropen: triggered after a popup has completely opened
+ * popupafterclose triggered when a popup has completely closed
+*/
+
+/**
+ class Popupwindow
+ The pop-up widget shows a list of items in a pop-up window in the middle of the screen. It automatically optimizes the pop-up window size within the screen.
+ To add a pop-up widget to the application, use the following code:
+ // Basic pop-up
+ <div id="center_info" data-role="popup" data-style="center_info">
+ <div data-role="text">
+ <p>
+ Pop-up dialog box, a child window that blocks user interaction in the parent window
+ </p>
+ </div>
+ </div>
+ // Pop-up with a title and button
+ <div id="center_title_1btn" data-role="popup" data-style="center_title_1btn">
+ <p data-role="title">
+ Pop-up title
+ </p>
+ <p data-role="text">
+ Pop-up dialog box
+ </p>
+ <div data-role="button-bg">
+ <input type="button" value="Text Button" />
+ </div>
+ </div>
+ The pop-up can define callbacks for events as described in the jQueryMobile documentation for pop-up events. <br/>You can use methods with the pop-up as described in the jQueryMobile documentation for pop-up methods.
-/* ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- *
- * jQuery Mobile Framework : "tabbar" plugin
- * Copyright (c) jQuery Project
- * Dual licensed under the MIT or GPL Version 2 licenses.
- * http://jquery.org/license
- * Authors: Jinhyuk Jun <jinhyuk.jun@samsung.com>
+ @deprecated 2.0 verisons
*/
/**
- * Tabbar can be created using data-role = "tabbar" inside footer
- * Framework determine which tabbar will display with tabbar attribute
- *
- * Examples:
- *
- * HTML markup for creating tabbar: ( 2 ~ 5 li item available )
- * icon can be changed data-icon attribute (customized icon need)
- * <div data-role="footer" data-position ="fixed">
- * <div data-role="tabbar">
- * <ul>
- * <li><a href="#" class="ui-btn-active">Menu</a></li>
- * <li><a href="#">Save</a></li>
- * <li><a href="#">Share</a></li>
- * </ul>
- * </div>
- * </div>
+ @property {String} data-style
+ Defines the pop-up window style.
+ The following styles are available:
+
+ center_info: basic pop-up message
+ center_title: pop-up message with a title
+ center_basic_1btn: pop-up message with 1 button
+ center_basic_2btn: pop-up message with 2 horizontal buttons
+ center_title_1btn: pop-up message with a title and 1 button
+ center_title_2btn: pop-up message with a title and 2 horizontal buttons
+ center_title_3btn: pop-up message with a title and 3 horizontal buttons
+ center_button_vertical: pop-up message with vertical buttons
+ center_checkbox: pop-up message with a check box
+ center_liststyle_1btn>: pop-up message with a list and 1 button
+ center_liststyle_2btn: pop-up message with a list and 2 horizontal buttons
+ center_liststyle_3btn: pop-up message with a list and 3 horizontal buttons
*/
(function ( $, undefined ) {
-
- $.widget( "tizen.tabbar", $.mobile.widget, {
+ $.widget( "tizen.popupwindow", $.tizen.widgetex, {
options: {
- iconpos: "top",
- grid: null,
- defaultList : 4,
- initSelector: ":jqmData(role='tabbar')"
+ theme: null,
+ overlayTheme: "s",
+ style: "custom",
+ disabled: false,
+ shadow: true,
+ corners: true,
+ fade: false,
+ opacity: 0.7,
+ widthRatio: 0.8612,
+ transition: $.mobile.defaultDialogTransition,
+ initSelector: ":jqmData(role='popupwindow')"
},
- _create: function () {
+ _htmlProto: {
+source:
- var $tabbar = this.element,
- $tabbtns,
- textpos,
- iconpos,
- theme = $.mobile.listview.prototype.options.theme, /* Get current theme */
- ww = window.innerWidth || $( window ).width(),
- wh = window.innerHeight || $( window ).height(),
- tabbarDividerLeft = "<div class='ui-tabbar-divider ui-tabbar-divider-left'></div>",
- tabbarDividerRight = "<div class='ui-tabbar-divider ui-tabbar-divider-right'></div>",
- isLandscape;
+ [ "<div><div>" ,
+ " <div id='popupwindow-screen' class='ui-selectmenu-screen ui-screen-hidden ui-popupwindow-screen'></div>" ,
+ " <div id='popupwindow-container' class='ui-popupwindow ui-popupwindow-padding ui-selectmenu-hidden ui-overlay-shadow ui-corner-all'></div>" ,
+ "</div>" ,
+ "</div>" ].join("")
+, ui: {
+ screen: "#popupwindow-screen",
+ container: "#popupwindow-container"
+ }
+ },
- isLandscape = ww > wh && ( ww - wh );
+ _setStyle: function () {
+ var popup = this.element,
+ style = popup.attr( 'data-style' );
- if ( isLandscape ) {
- $tabbar.removeClass( "ui-portrait-tabbar" ).addClass( "ui-landscape-tabbar" );
- } else {
- $tabbar.removeClass( "ui-landscape-tabbar" ).addClass( "ui-portrait-tabbar" );
+ if ( style ) {
+ this.options.style = style;
}
- if ( $tabbar.find( "a" ).length ) {
- $tabbtns = $tabbar.find( "a" );
- iconpos = $tabbtns.filter( ":jqmData(icon)" ).length ? this.options.iconpos : undefined;
- textpos = $tabbtns.html().length ? true : false;
+ popup.addClass( this.options.style );
+ popup.find( ":jqmData(role='title')" )
+ .wrapAll( "<div class='popup-title'></div>" );
+ popup.find( ":jqmData(role='text')" )
+ .wrapAll( "<div class='popup-text'></div>" );
+ popup.find( ":jqmData(role='button-bg')" )
+ .wrapAll( "<div class='popup-button-bg'></div>" );
+ popup.find( ":jqmData(role='check-bg')" )
+ .wrapAll( "<div class='popup-check-bg'></div>" );
+ popup.find( ":jqmData(role='scroller-bg')" )
+ .addClass( "popup-scroller-bg" );
+ popup.find( ":jqmData(role='text-bottom-bg')" )
+ .wrapAll( "<div class='popup-text-bottom-bg'></div>" );
+ popup.find( ":jqmData(role='text-left')" )
+ .wrapAll( "<div class='popup-text-left'></div>" );
+ popup.find( ":jqmData(role='text-right')" )
+ .wrapAll( "<div class='popup-text-right'></div>" );
+ popup.find( ":jqmData(role='progress-bg')" )
+ .wrapAll( "<div class='popup-progress-bg'></div>" );
+ },
+
+ _create: function () {
+ console.warn("popupwindow() was deprecated. use popup() instead.");
+ var thisPage = this.element.closest(":jqmData(role='page')"),
+ self = this;
+
+ if ( thisPage.length === 0 ) {
+ thisPage = $("body");
}
- if ( $tabbar.parents( ".ui-header" ).length && $tabbar.parents( ".ui-scrollview-view" ).length ) {
- $tabbar.find( "li" ).addClass( "tabbar-scroll-li" );
- $tabbar.find( "ul" ).addClass( "tabbar-scroll-ul" );
+ this._ui.placeholder =
+ $( "<div><!-- placeholder for " + this.element.attr("id") + " --></div>" )
+ .css("display", "none")
+ .insertBefore( this.element );
- /* add shadow divider */
- $( tabbarDividerLeft ).appendTo( $tabbar.parents( ".ui-scrollview-clip" ) );
- $( tabbarDividerRight ).appendTo( $tabbar.parents( ".ui-scrollview-clip" ) );
+ thisPage.append( this._ui.screen );
+ this._ui.container.insertAfter( this._ui.screen );
+ this._ui.container.append( this.element );
- $( ".ui-tabbar-divider-left" ).hide();
- $( ".ui-tabbar-divider-right" ).hide();
+ this._setStyle();
- /* add width calculation*/
- if ( $tabbar.parents( ".ui-scrollview-view" ).data("default-list") ) {
- this.options.defaultList = $tabbar.parents( ".ui-scrollview-view" ).data( "default-list" );
+ this._isOpen = false;
+
+ this._ui.screen.bind( "vclick", function ( e ) {
+ self.close();
+ return false;
+ } );
+
+ this.element.bind( "vclick", function ( e ) {
+ if ( $( e.target ).is("ui-btn-ctxpopup-close") ) {
+ self.close();
}
- $tabbar.find( "li" ).css( "width", window.innerWidth / this.options.defaultList + "px" );
+ } );
+ },
+
+ destroy: function () {
+ this.element.insertBefore( this._ui.placeholder );
+
+ this._ui.placeholder.remove();
+ this._ui.container.remove();
+ this._ui.screen.remove();
+ this.element.triggerHandler("destroyed");
+ $.Widget.prototype.destroy.call( this );
+ },
+
+ _placementCoords: function ( x, y, cw, ch ) {
+ var screenHeight = $( window ).height(),
+ screenWidth = $( window ).width(),
+ halfheight = ch / 2,
+ maxwidth = parseFloat( this._ui.container.css( "max-width" ) ),
+ roomtop = y,
+ roombot = screenHeight - y,
+ newtop,
+ newleft;
+
+ if ( roomtop > ch / 2 && roombot > ch / 2 ) {
+ newtop = y - halfheight;
} else {
- if ( $tabbar.find( "ul" ).children().length ) {
- $tabbar.addClass( "ui-navbar" )
- .find( "ul" )
- .grid( { grid: this.options.grid } );
- }
+ newtop = roomtop > roombot ? screenHeight - ch - 30 : 30;
}
- if ( $tabbar.parents( ".ui-footer" ).length ) {
- $tabbar.find( "li" ).addClass( "ui-tab-btn-style" );
- }
+ if ( cw < maxwidth ) {
+ newleft = ( screenWidth - cw ) / 2;
+ } else {
+ newleft = x - cw / 2;
- /* title tabbar */
- if ( $tabbar.siblings( ".ui-title" ).length ) {
- $tabbar.parents( ".ui-header" ).addClass( "ui-title-tabbar" );
+ if ( newleft < 10 ) {
+ newleft = 10;
+ } else if ( ( newleft + cw ) > screenWidth ) {
+ newleft = screenWidth - cw - 10;
+ }
}
- if ( !iconpos ) {
- $tabbar.addClass( "ui-tabbar-noicons" );
- }
- if ( !textpos ) {
- $tabbar.addClass( "ui-tabbar-notext" );
- }
- if ( textpos && iconpos ) {
- $tabbar.parents( ".ui-header" ).addClass( "ui-title-tabbar-multiline" );
- }
+ return { x : newleft, y : newtop };
+ },
- if ( $tabbar.find( "a" ).length ) {
- $tabbtns.buttonMarkup({
- corners: false,
- shadow: false,
- iconpos: iconpos
- });
- }
+ _setPosition: function ( x_where, y_where ) {
+ var x = ( undefined === x_where ? $( window ).width() / 2 : x_where ),
+ y = ( undefined === y_where ? $( window ).height() / 2 : y_where ),
+ coords,
+ ctxpopup = this.element.data("ctxpopup"),
+ popupWidth,
+ menuHeight,
+ menuWidth,
+ screenHeight,
+ screenWidth,
+ roomtop,
+ roombot,
+ halfheight,
+ maxwidth,
+ newtop,
+ newleft;
- if ( $tabbar.find( ".ui-state-persist" ).length ) {
- $tabbar.addClass( "ui-tabbar-persist" );
+ if ( !ctxpopup ) {
+ popupWidth = $( window ).width() * this.options.widthRatio;
+ this._ui.container.css( "width", popupWidth );
+
+ if ( this._ui.container.outerWidth() > $( window ).width() ) {
+ this._ui.container.css( {"max-width" : $( window ).width() - 30} );
+ }
}
- $tabbar.delegate( "a", "vclick", function ( event ) {
- $tabbtns.not( ".ui-state-persist" ).removeClass( $.mobile.activeBtnClass );
- $( this ).addClass( $.mobile.activeBtnClass );
- });
+ coords = this._placementCoords( x, y,
+ this._ui.container.outerWidth(),
+ this._ui.container.outerHeight() );
- $tabbar.addClass( "ui-tabbar");
+ menuHeight = this._ui.container.innerHeight();
+ menuWidth = this._ui.container.innerWidth();
+ screenHeight = $( window ).height();
+ screenWidth = $( window ).width();
+ roomtop = y;
+ roombot = screenHeight - y;
+ halfheight = menuHeight / 2;
+ maxwidth = parseFloat( this._ui.container.css( "max-width" ) );
+ newtop = ( screenHeight - menuHeight ) / 2;
- $( document ).bind( "pagebeforeshow", function ( event, ui ) {
- var footer_filter = $( event.target ).find( ":jqmData(role='footer')" ),
- tabbar_filter = footer_filter.find( ":jqmData(role='tabbar')" ),
- $elFooterMore = tabbar_filter.siblings( ":jqmData(icon='naviframe-more')" ),
- $elFooterBack = tabbar_filter.siblings( ".ui-btn-back" );
+ if ( !maxwidth || menuWidth < maxwidth ) {
+ newleft = ( screenWidth - menuWidth ) / 2;
+ } else {
+ newleft = x - menuWidth / 2;
- footer_filter
- .css( "position", "fixed" )
- .css( "bottom", 0 )
- .css( "height", tabbar_filter.height() );
- if ( $elFooterMore.length ) {
- tabbar_filter.addClass( "ui-tabbar-margin-more" );
- }
- if ( $elFooterBack.length ) {
- tabbar_filter.addClass( "ui-tabbar-margin-back" );
+ if ( newleft < 30 ) {
+ newleft = 30;
+ } else if ( ( newleft + menuWidth ) > screenWidth ) {
+ newleft = screenWidth - menuWidth - 30;
}
- });
+ }
- $tabbar.bind( "touchstart vmousedown", function ( e ) {
- var $tabbarScroll = $( e.target ).parents( ".ui-scrollview-view" );
- if ( $tabbarScroll.offset() ) {
- if ( $tabbarScroll.offset().left < 0 ) {
- $( ".ui-tabbar-divider-left" ).show();
- } else {
- $( ".ui-tabbar-divider-left" ).hide();
- }
- if ( ( $tabbarScroll.width() - $tabbarScroll.parents( ".ui-scrollview-clip" ).width() ) == Math.abs( $tabbarScroll.offset().left ) ) {
- $( ".ui-tabbar-divider-right" ).hide();
- } else {
- $( ".ui-tabbar-divider-right" ).show();
- }
- }
+ if ( ctxpopup ) {
+ newtop = coords.y;
+ newleft = coords.x;
+ }
+
+ this._ui.container.css({
+ top: newtop,
+ left: newleft
});
- this._bindTabbarEvents();
- this._initTabbarAnimation();
+ this._ui.screen.css( "height", screenHeight );
},
+ open: function ( x_where, y_where, backgroundclose ) {
+ var self = this,
+ zIndexMax = 0;
- _initTabbarAnimation: function () {
- var isScrollingStart = false,
- isScrollingEnd = false;
- $( document ).bind( "scrollstart.tabbar", function ( e ) {
- if ( $( e.target ).find( ".ui-tabbar" ).length ) {
- isScrollingStart = true;
- isScrollingEnd = false;
- }
- });
+ if ( this._isOpen || this.options.disabled ) {
+ return;
+ }
- $( document ).bind( "scrollstop.tabbar", function ( e ) {
- var $tabbarScrollview = $( e.target ),
- $elTabbar = $( e.target ).find( ".ui-tabbar" ),
- $elTabbarLI = $( e.target ).find( ".ui-tabbar li" ),
- $minElement = $elTabbarLI.eq( 0 ),
- minElementIndexVal,
- minElementIndex = -1;
+ $( document ).find("*").each( function () {
+ var el = $( this ),
+ zIndex = parseInt( el.css("z-index"), 10 );
- isScrollingEnd = true;
- if ( $elTabbar.length && isScrollingStart == true ) {
- minElementIndexVal = Math.abs( $elTabbarLI.eq( 0 ).offset().left );
- $elTabbarLI.each( function ( i ) {
- var offset = $elTabbarLI.eq( i ).offset();
+ if ( !( el.is( self._ui.container ) ||
+ el.is( self._ui.screen ) ||
+ isNaN( zIndex ))) {
+ zIndexMax = Math.max( zIndexMax, zIndex );
+ }
+ } );
- if ( Math.abs( offset.left ) < minElementIndexVal ) {
- minElementIndexVal = Math.abs( offset.left );
- minElementIndex = i;
- $minElement = $elTabbarLI.eq( i );
- }
- });
+ this._ui.screen.css( "height", $( window ).height() );
- if ( $tabbarScrollview.length && isScrollingStart == isScrollingEnd && minElementIndex != -1) {
- isScrollingStart = false;
- $tabbarScrollview.scrollview( "scrollTo", -( window.innerWidth / $elTabbar.data( "defaultList" ) * minElementIndex ) , 0, 357);
- }
+ if ( backgroundclose ) {
+ this._ui.screen.css( "opacity", 0 )
+ .removeClass("ui-screen-hidden");
+ } else {
+ this._ui.removeClass("ui-screen-hidden");
+
+ if ( this.options.fade ) {
+ this._ui.screen.animate( {opacity: this.options.opacity}, "fast" );
+ } else {
+ this._ui.screen.css( {opacity: this.options.opacity} );
}
+ }
- $( ".ui-tabbar-divider-left" ).hide();
- $( ".ui-tabbar-divider-right" ).hide();
- });
- },
+ this._setPosition( x_where, y_where );
- _bindTabbarEvents: function () {
- var $tabbar = this.element;
+ this.element.trigger("popupbeforeposition");
- $( window ).bind( "orientationchange", function ( e, ui ) {
- var ww = window.innerWidth || $( window ).width(),
- wh = window.innerHeight || $( window ).height(),
- isLandscape = ww > wh && ( ww - wh );
+ this._ui.container
+ .removeClass("ui-selectmenu-hidden")
+ .addClass("in")
+ .animationComplete( function () {
+ self.element.trigger("popupafteropen");
+ } );
- if ( isLandscape ) {
- $tabbar.removeClass( "ui-portrait-tabbar" ).addClass( "ui-landscape-tabbar" );
- } else {
- $tabbar.removeClass( "ui-landscape-tabbar" ).addClass( "ui-portrait-tabbar" );
- }
- });
- },
+ this._isOpen = true;
- _setDisabled: function ( value, cnt ) {
- this.element.find( "li" ).eq( cnt ).attr( "disabled", value );
- this.element.find( "li" ).eq( cnt ).attr( "aria-disabled", value );
- },
+ if ( !this._reflow ) {
+ this._reflow = function () {
+ if ( !self._isOpen ) {
+ return;
+ }
- disable: function ( cnt ) {
- this._setDisabled( true, cnt );
- this.element.find( "li" ).eq( cnt ).addClass( "ui-disabled" );
- },
+ self._setPosition( x_where, y_where );
+ };
- enable: function ( cnt ) {
- this._setDisabled( false, cnt );
- this.element.find( "li" ).eq( cnt ).removeClass( "ui-disabled" );
- }
- });
+ $( window ).bind( "resize", this._reflow );
+ }
+ },
- //auto self-init widgets
- $( document ).bind( "pagecreate create", function ( e ) {
- $( $.tizen.tabbar.prototype.options.initSelector, e.target ).tabbar();
- });
-}( jQuery ) );
+ close: function () {
+ if ( !this._isOpen ) {
+ return;
+ }
+ if ( this._reflow ) {
+ $( window ).unbind( "resize", this._reflow );
+ this._reflow = null;
+ }
+ var self = this,
+ hideScreen = function () {
+ self._ui.screen.addClass("ui-screen-hidden");
+ self._isOpen = false;
+ };
-/*
- * This software is licensed under the MIT licence (as defined by the OSI at
- * http://www.opensource.org/licenses/mit-license.php)
- *
- * ***************************************************************************
- * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- * Copyright (c) 2011 by Intel Corporation Ltd.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- * ***************************************************************************
- */
+ this._ui.container.removeClass("in").addClass("reverse out");
-( function ($, undefined) {
+ if ( this.options.transition === "none" ) {
+ this._ui.container
+ .addClass("ui-selectmenu-hidden")
+ .removeAttr("style");
+ this.element.trigger("popupafterclose");
+ } else {
+ this._ui.container.animationComplete( function () {
+ self._ui.container
+ .removeClass("reverse out")
+ .addClass("ui-selectmenu-hidden")
+ .removeAttr("style");
+ self.element.trigger("popupafterclose");
+ } );
+ }
- $.widget( "tizen.triangle", $.tizen.widgetex, {
- options: {
- extraClass: "",
- offset: null,
- color: null,
- location: "top",
- initSelector: ":jqmData(role='triangle')"
+ if ( this.options.fade ) {
+ this._ui.screen.animate( {opacity: 0}, "fast", hideScreen );
+ } else {
+ hideScreen();
+ }
},
- _create: function () {
- var triangle = $( "<div></div>", {"class" : "ui-triangle"} );
+ _realSetTheme: function ( dst, theme ) {
+ var classes = ( dst.attr("class") || "" ).split(" "),
+ alreadyAdded = true,
+ currentTheme = null,
+ matches;
- $.extend(this, {
- _triangle: triangle
- });
+ while ( classes.length > 0 ) {
+ currentTheme = classes.pop();
+ matches = currentTheme.match(/^ui-body-([a-z])$/);
- this.element.addClass( "ui-triangle-container" ).append( triangle );
+ if ( matches && matches.length > 1 ) {
+ currentTheme = matches[1];
+ break;
+ } else {
+ currentTheme = null;
+ }
+ }
+
+ dst.removeClass( "ui-body-" + currentTheme );
+ if ( ( theme || "" ).match(/[a-z]/) ) {
+ dst.addClass( "ui-body-" + theme );
+ }
},
- _doCSS: function () {
- var location = ( this.options.location || "top" ),
- offsetCoord = ( ($.inArray(location, ["top", "bottom"]) === -1) ? "top" : "left"),
- cssArg = {
- "border-bottom-color" : "top" === location ? this.options.color : "transparent",
- "border-top-color" : "bottom" === location ? this.options.color : "transparent",
- "border-left-color" : "right" === location ? this.options.color : "transparent",
- "border-right-color" : "left" === location ? this.options.color : "transparent"
- };
+ _setTheme: function ( value ) {
+ this._realSetTheme( this.element, value );
+ this.options.theme = value;
+ this.element.attr( "data-" + ( $.mobile.ns || "" ) + "theme", value );
+ },
- cssArg[offsetCoord] = this.options.offset;
+ _setOverlayTheme: function ( value ) {
+ this._realSetTheme( this._ui.container, value );
+ this.options.overlayTheme = value;
+ this.element.attr( "data-" + ( $.mobile.ns || "" ) + "overlay-theme", value );
+ },
- this._triangle.removeAttr( "style" ).css( cssArg );
+ _setShadow: function ( value ) {
+ this.options.shadow = value;
+ this.element.attr( "data-" + ( $.mobile.ns || "" ) + "shadow", value );
+ this._ui.container[value ? "addClass" : "removeClass"]("ui-overlay-shadow");
},
- _setOffset: function ( value ) {
- this.options.offset = value;
- this.element.attr( "data-" + ($.mobile.ns || "") + "offset", value );
- this._doCSS();
+ _setCorners: function ( value ) {
+ this.options.corners = value;
+ this.element.attr( "data-" + ( $.mobile.ns || "" ) + "corners", value );
+ this._ui.container[value ? "addClass" : "removeClass"]("ui-corner-all");
},
- _setExtraClass: function ( value ) {
- this._triangle.addClass( value );
- this.options.extraClass = value;
- this.element.attr( "data-" + ($.mobile.ns || "") + "extra-class", value );
+ _setFade: function ( value ) {
+ this.options.fade = value;
+ this.element.attr( "data-" + ( $.mobile.ns || "" ) + "fade", value );
},
- _setColor: function ( value ) {
- this.options.color = value;
- this.element.attr( "data-" + ($.mobile.ns || "") + "color", value );
- this._doCSS();
+ _setTransition: function ( value ) {
+ this._ui.container
+ .removeClass( this.options.transition || "" )
+ .addClass( value );
+ this.options.transition = value;
+ this.element.attr( "data-" + ( $.mobile.ns || "" ) + "transition", value );
},
- _setLocation: function ( value ) {
- this.element
- .removeClass( "ui-triangle-container-" + this.options.location )
- .addClass( "ui-triangle-container-" + value );
- this._triangle
- .removeClass( "ui-triangle-" + this.options.location )
- .addClass( "ui-triangle-" + value );
+ _setDisabled: function ( value ) {
+ $.Widget.prototype._setOption.call( this, "disabled", value );
+ if ( value ) {
+ this.close();
+ }
+ }
+ });
- this.options.location = value;
- this.element.attr( "data-" + ($.mobile.ns || "") + "location", value );
+ $.tizen.popupwindow.bindPopupToButton = function ( btn, popup ) {
+ if ( btn.length === 0 || popup.length === 0 ) {
+ return;
+ }
- this._doCSS();
+ var btnVClickHandler = function ( e ) {
+ if ( !popup.jqmData("overlay-theme-set") ) {
+ popup.popupwindow( "option", "overlayTheme", btn.jqmData("theme") );
+ }
+
+ popup.popupwindow( "open",
+ btn.offset().left + btn.outerWidth() / 2,
+ btn.offset().top + btn.outerHeight() / 2 );
+
+ return false;
+ };
+
+ if ( ( popup.popupwindow("option", "overlayTheme") || "" ).match(/[a-z]/) ) {
+ popup.jqmData( "overlay-theme-set", true );
}
- });
+
+ btn
+ .attr({
+ "aria-haspopup": true,
+ "aria-owns": btn.attr("href")
+ })
+ .removeAttr("href")
+ .bind( "vclick", btnVClickHandler );
+
+ popup.bind( "destroyed", function () {
+ btn.unbind( "vclick", btnVClickHandler );
+ } );
+ };
$( document ).bind( "pagecreate create", function ( e ) {
- $($.tizen.triangle.prototype.options.initSelector, e.target)
- .not(":jqmData(role='none'), :jqmData(role='nojs')")
- .triangle();
- });
+ $( $.tizen.popupwindow.prototype.options.initSelector, e.target )
+ .not(":jqmData(role='none'), :jqmData(role='nojs')")
+ .popupwindow();
-}(jQuery) );
+ $( "a[href^='#']:jqmData(rel='popupwindow')", e.target ).each( function () {
+ $.tizen.popupwindow.bindPopupToButton( $( this ), $( $( this ).attr("href") ) );
+ });
+ });
+}( jQuery ));
-/*
- * jQuery Mobile Widget @VERSION
- *
- * This software is licensed under the MIT licence (as defined by the OSI at
- * http://www.opensource.org/licenses/mit-license.php)
- *
- * ***************************************************************************
+/* ***************************************************************************
* Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
- * Copyright (c) 2011 by Intel Corporation Ltd.
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ***************************************************************************
- *
- * Authors: Gabriel Schulhof <gabriel.schulhof@intel.com>,
- * Elliot Smith <elliot.smith@intel.com>
- * Hyunjung Kim <hjnim.kim@samsung.com>
*/
-
/*
- * % Popupwindow widget do not use anymore(will be deprecated, internal use only)
- *
- *
- * Shows other elements inside a popup window.
- *
- * To apply, add the attribute data-role="popupwindow" to a <div> element inside
- * a page. Alternatively, call popupwindow()
- * on an element, eg :
- *
- * $("#mypopupwindowContent").popupwindow();
- * where the html might be :
- * <div id="mypopupwindowContent"></div>
- *
- * To trigger the popupwindow to appear, it is necessary to make a call to its
- * 'open()' method. This is typically done by binding a function to an event
- * emitted by an input element, such as a the clicked event emitted by a button
- * element. The open() method takes two arguments, specifying the x and y
- * screen coordinates of the center of the popup window.
+* jQuery Mobile Framework : "textinput" plugin for text inputs, textareas
+* Copyright (c) jQuery Project
+* Dual licensed under the MIT or GPL Version 2 licenses.
+* http://jquery.org/license
+* Authors: Jinhyuk Jun <jinhyuk.jun@samsung.com>
+* Wongi Lee <wongi11.lee@samsung.com>
+*/
- * You can associate a button with a popup window like this:
- * <div id="mypopupContent" style="display: table;" data-role="popupwindow">
- * <table>
- * <tr> <td>Eenie</td> <td>Meenie</td> <td>Mynie</td> <td>Mo</td> </tr>
- * <tr> <td>Catch-a</td> <td>Tiger</td> <td>By-the</td> <td>Toe</td> </tr>
- * <tr> <td>If-he</td> <td>Hollers</td> <td>Let-him</td> <td>Go</td> </tr>
- * <tr> <td>Eenie</td> <td>Meenie</td> <td>Mynie</td> <td>Mo</td> </tr>
- * </table>
- * </div>
- * <a href="#myPopupContent" data-rel="popupwindow" data-role="button">Show popup</a>
- *
- * Options:
- *
- * theme: String; the theme for the popupwindow contents
- * Default: null
- *
- * overlayTheme: String; the theme for the popupwindow
- * Default: null
+/**
+ * Searchbar can be created using <input> element with type=search
+ * <input type="search" name="search" id="search1" value="" />
*
- * shadow: Boolean; display a shadow around the popupwindow
- * Default: true
+ * Searchbar can be inserted 3 cases
+ * content : seachbar behave same as content element
+ * header : searchbar placed below title(header), It doesn't move when scrolling page
+ * inside optionheader : Searchbar placed inside optionheader, searchbar can be seen only expand optionheader
*
- * corners: Boolean; display a shadow around the popupwindow
- * Default: true
+ * Examples:
*
- * fade: Boolean; fades the opening and closing of the popupwindow
+ * HTML markup for creating Searchbar
+ * <input type="search"/>
*
- * transition: String; the transition to use when opening or closing
- * a popupwindow
- * Default: $.mobile.defaultDialogTransition
+ * How to make searchbar in content
+ * <input type="search" name="" id="" value="" />
*
- * Events:
- * popupbeforeposition: triggered after a popup has completed preparations for opening, but has not yet opened
- * popupafteropen: triggered after a popup has completely opened
- * popupafterclose triggered when a popup has completely closed
-*/
-
-/**
- class Popupwindow
- The pop-up widget shows a list of items in a pop-up window in the middle of the screen. It automatically optimizes the pop-up window size within the screen.
- To add a pop-up widget to the application, use the following code:
-
- // Basic pop-up
- <div id="center_info" data-role="popup" data-style="center_info">
- <div data-role="text">
- <p>
- Pop-up dialog box, a child window that blocks user interaction in the parent window
- </p>
- </div>
- </div>
- // Pop-up with a title and button
- <div id="center_title_1btn" data-role="popup" data-style="center_title_1btn">
- <p data-role="title">
- Pop-up title
- </p>
- <p data-role="text">
- Pop-up dialog box
- </p>
- <div data-role="button-bg">
- <input type="button" value="Text Button" />
- </div>
- </div>
-
- The pop-up can define callbacks for events as described in the jQueryMobile documentation for pop-up events. <br/>You can use methods with the pop-up as described in the jQueryMobile documentation for pop-up methods.
-
- @deprecated 2.0 verisons
+ * How to make cancel button in searchbar
+ * <div data-role="header" data-position ="fixed" >
+ * <h1>Searchbar</h1>
+ * <input type="search" data-cancel-btn=true name="" id="" value="" />
+ * </div>
+ *
+ * How to make icon in front of searchbar
+ * <div data-role="header" data-position ="fixed" >
+ * <h1>Searchbar</h1>
+ * <input type="search" data-icon="call" name="" id="" value="" />
+ * </div>
*/
/**
- @property {String} data-style
- Defines the pop-up window style.
- The following styles are available:
+ @class SearchBar
+ The search bar widget is used to search for page content. This widget can be placed in the header, option header, or page content.
- center_info: basic pop-up message
- center_title: pop-up message with a title
- center_basic_1btn: pop-up message with 1 button
- center_basic_2btn: pop-up message with 2 horizontal buttons
- center_title_1btn: pop-up message with a title and 1 button
- center_title_2btn: pop-up message with a title and 2 horizontal buttons
- center_title_3btn: pop-up message with a title and 3 horizontal buttons
- center_button_vertical: pop-up message with vertical buttons
- center_checkbox: pop-up message with a check box
- center_liststyle_1btn>: pop-up message with a list and 1 button
- center_liststyle_2btn: pop-up message with a list and 2 horizontal buttons
- center_liststyle_3btn: pop-up message with a list and 3 horizontal buttons
+ To add a search bar widget to the application, use the following code:
+
+ <label for="search-basic">Search Input:</label>
+ <input type="search" name="search" id="searc-basic" value="" data-mini="true" />
+
+ Tizen supports many search bar options as described in the jQueryMobile documentation for search bar options.
+ The search bar can define callbacks for events as described in the jQueryMobile documentation for search bar events.
+ You can use methods with the search bar as described in the jQueryMobile documentation for search bar methods.
*/
(function ( $, undefined ) {
- $.widget( "tizen.popupwindow", $.tizen.widgetex, {
+
+ $.widget( "tizen.searchbar", $.mobile.widget, {
options: {
theme: null,
- overlayTheme: "s",
- style: "custom",
- disabled: false,
- shadow: true,
- corners: true,
- fade: false,
- opacity: 0.7,
- widthRatio: 0.8612,
- transition: $.mobile.defaultDialogTransition,
- initSelector: ":jqmData(role='popupwindow')"
+ initSelector: "input[type='search'],:jqmData(type='search'), input[type='tizen-search'],:jqmData(type='tizen-search')"
},
- _htmlProto: {
-source:
+ _create: function () {
+ var input = this.element,
+ o = this.options,
+ theme = o.theme || $.mobile.getInheritedTheme( this.element, "c" ),
+ themeclass = " ui-body-" + theme,
+ focusedEl,
+ clearbtn,
+ cancelbtn,
+ defaultText,
+ defaultTextClass,
+ trimedText,
+ newClassName,
+ newStyle,
+ newDiv,
+ searchimage,
+ inputedText,
+ useCancelBtn = false,
+ frontIcon = false;
- [ "<div><div>" ,
- " <div id='popupwindow-screen' class='ui-selectmenu-screen ui-screen-hidden ui-popupwindow-screen'></div>" ,
- " <div id='popupwindow-container' class='ui-popupwindow ui-popupwindow-padding ui-selectmenu-hidden ui-overlay-shadow ui-corner-all'></div>" ,
- "</div>" ,
- "</div>" ].join("")
-, ui: {
- screen: "#popupwindow-screen",
- container: "#popupwindow-container"
+ $( "label[for='" + input.attr( "id" ) + "']" ).addClass( "ui-input-text" );
+
+ if ( typeof input[0].autocorrect !== "undefined" && !$.support.touchOverflow ) {
+ // Set the attribute instead of the property just in case there
+ // is code that attempts to make modifications via HTML.
+ input[0].setAttribute( "autocorrect", "off" );
+ input[0].setAttribute( "autocomplete", "off" );
}
- },
- _setStyle: function () {
- var popup = this.element,
- style = popup.attr( 'data-style' );
+ focusedEl = input.wrap( "<div class='ui-input-search ui-shadow-inset ui-corner-all ui-btn-shadow" + themeclass + "'></div>" ).parent();
- if ( style ) {
- this.options.style = style;
+ if ( $( this.element ).data( "cancel-btn" ) === true ) {
+ useCancelBtn = true;
+ focusedEl.addClass( "ui-input-search-default" );
+ }
+ if ( $( this.element ).data( "icon" ) != undefined ) {
+ frontIcon = true;
+ focusedEl.addClass( "ui-search-bar-icon" );
}
- popup.addClass( this.options.style );
- popup.find( ":jqmData(role='title')" )
- .wrapAll( "<div class='popup-title'></div>" );
- popup.find( ":jqmData(role='text')" )
- .wrapAll( "<div class='popup-text'></div>" );
- popup.find( ":jqmData(role='button-bg')" )
- .wrapAll( "<div class='popup-button-bg'></div>" );
- popup.find( ":jqmData(role='check-bg')" )
- .wrapAll( "<div class='popup-check-bg'></div>" );
- popup.find( ":jqmData(role='scroller-bg')" )
- .addClass( "popup-scroller-bg" );
- popup.find( ":jqmData(role='text-bottom-bg')" )
- .wrapAll( "<div class='popup-text-bottom-bg'></div>" );
- popup.find( ":jqmData(role='text-left')" )
- .wrapAll( "<div class='popup-text-left'></div>" );
- popup.find( ":jqmData(role='text-right')" )
- .wrapAll( "<div class='popup-text-right'></div>" );
- popup.find( ":jqmData(role='progress-bg')" )
- .wrapAll( "<div class='popup-progress-bg'></div>" );
- },
+ clearbtn = $( "<a href='#' class='ui-input-clear' title='clear text'>clear text</a>" )
+ .bind('click', function ( event ) {
+ if ( input.attr( "disabled" ) == "disabled" ) {
+ return false;
+ }
+ input
+ .val( "" )
+ .focus()
+ .trigger( "change" );
+ clearbtn.addClass( "ui-input-clear-hidden" );
+ event.preventDefault();
+ })
+ .appendTo( focusedEl )
+ .buttonMarkup({
+ icon: "deleteSearch",
+ iconpos: "notext",
+ corners: true,
+ shadow: true
+ });
- _create: function () {
- console.warn("popupwindow() was deprecated. use popup() instead.");
- var thisPage = this.element.closest(":jqmData(role='page')"),
- self = this;
+ function toggleClear() {
+ setTimeout(function () {
+ clearbtn.toggleClass( "ui-input-clear-hidden", !input.val() );
+ }, 0);
+ }
- if ( thisPage.length === 0 ) {
- thisPage = $("body");
+ function showCancel() {
+ focusedEl
+ .addClass( "ui-input-search-default" )
+ .removeClass( "ui-input-search-wide" );
+ cancelbtn
+ .addClass( "ui-btn-cancel-show" )
+ .removeClass( "ui-btn-cancel-hide" );
}
- this._ui.placeholder =
- $( "<div><!-- placeholder for " + this.element.attr("id") + " --></div>" )
- .css("display", "none")
- .insertBefore( this.element );
+ function hideCancel() {
+ focusedEl
+ .addClass( "ui-input-search-wide" )
+ .removeClass( "ui-input-search-default" );
+ cancelbtn
+ .addClass( "ui-btn-cancel-hide" )
+ .removeClass( "ui-btn-cancel-show" );
+ toggleClear();
+ }
- thisPage.append( this._ui.screen );
- this._ui.container.insertAfter( this._ui.screen );
- this._ui.container.append( this.element );
+ function makeFrontIcon() {
+ var IconStyle = $( input ).jqmData( "icon" ),
+ frontIcon = $( "<div data-role='button' data-style='circle'></div>" );
- this._setStyle();
+ frontIcon
+ .appendTo( focusedEl.parent() )
+ .buttonMarkup( {
+ icon: IconStyle,
+ iconpos: "notext",
+ corners: true,
+ shadow: true
+ } );
+ frontIcon.addClass( "ui-btn-search-front-icon" );
+ }
- this._isOpen = false;
+ toggleClear();
- this._ui.screen.bind( "vclick", function ( e ) {
- self.close();
- return false;
- } );
+ input.bind( 'paste cut keyup focus change blur', toggleClear );
- this.element.bind( "vclick", function ( e ) {
- if ( $( e.target ).is("ui-btn-ctxpopup-close") ) {
- self.close();
- }
- } );
- },
+ //SLP --start search bar with cancel button
+ focusedEl.wrapAll( "<div class='input-search-bar'></div>" );
+ searchimage = $("<div class='ui-image-search'></div>").appendTo( focusedEl );
- destroy: function () {
- this.element.insertBefore( this._ui.placeholder );
+ if ( frontIcon ) {
+ makeFrontIcon();
+ }
- this._ui.placeholder.remove();
- this._ui.container.remove();
- this._ui.screen.remove();
- this.element.triggerHandler("destroyed");
- $.Widget.prototype.destroy.call( this );
- },
+ if ( useCancelBtn ) {
+ cancelbtn = $( "<div data-role='button' class='ui-input-cancel' title='clear text'>Cancel</div>" )
+ .bind('click', function ( event ) {
+ if ( input.attr( "disabled" ) == "disabled" ) {
+ return false;
+ }
+ event.preventDefault();
+ event.stopPropagation();
+
+ input
+ .val( "" )
+ .blur()
+ .trigger( "change" );
+
+ if ( useCancelBtn ) {
+ hideCancel();
+ }
+ } )
+ .appendTo( focusedEl.parent() )
+ .buttonMarkup( {
+ iconpos: "cancel",
+ corners: true,
+ shadow: true
+ } );
+ }
+
+ // Input Focused
+ input
+ .focus( function () {
+ if ( input.attr( "disabled" ) == "disabled" ) {
+ return false;
+ }
+ if ( useCancelBtn ) {
+ showCancel();
+ }
+ focusedEl.addClass( $.mobile.focusClass );
+ })
+ .blur(function () {
+ focusedEl.removeClass( $.mobile.focusClass );
+ });
+
+ // Default Text
+ defaultText = input.jqmData( "default-text" );
+
+ if ( ( defaultText != undefined ) && ( defaultText.length > 0 ) ) {
+ defaultTextClass = "ui-input-default-text";
+ trimedText = defaultText.replace(/\s/g, "");
- _placementCoords: function ( x, y, cw, ch ) {
- var screenHeight = $( window ).height(),
- screenWidth = $( window ).width(),
- halfheight = ch / 2,
- maxwidth = parseFloat( this._ui.container.css( "max-width" ) ),
- roomtop = y,
- roombot = screenHeight - y,
- newtop,
- newleft;
+ /* Make new class for default text string */
+ newClassName = defaultTextClass + "-" + trimedText;
+ newStyle = $( "<style>" + '.' + newClassName + ":after" + "{content:" + "'" + defaultText + "'" + "}" + "</style>" );
+ $( 'html > head' ).append( newStyle );
- if ( roomtop > ch / 2 && roombot > ch / 2 ) {
- newtop = y - halfheight;
- } else {
- newtop = roomtop > roombot ? screenHeight - ch - 30 : 30;
- }
+ /* Make new empty <DIV> for default text */
+ newDiv = $( "<div></div>" );
- if ( cw < maxwidth ) {
- newleft = ( screenWidth - cw ) / 2;
- } else {
- newleft = x - cw / 2;
+ /* Add class and append new div */
+ newDiv.addClass( defaultTextClass );
+ newDiv.addClass( newClassName );
+ newDiv.tap( function ( event ) {
+ input.blur();
+ input.focus();
+ } );
- if ( newleft < 10 ) {
- newleft = 10;
- } else if ( ( newleft + cw ) > screenWidth ) {
- newleft = screenWidth - cw - 10;
- }
+ input.parent().append( newDiv );
+
+ /* When focus, default text will be hide. */
+ input
+ .focus( function () {
+ input.parent().find( "div.ui-input-default-text" ).addClass( "ui-input-default-hidden" );
+ } )
+ .blur( function () {
+ var inputedText = input.val();
+ if ( inputedText.length > 0 ) {
+ input.parent().find( "div.ui-input-default-text" ).addClass( "ui-input-default-hidden" );
+ } else {
+ input.parent().find( "div.ui-input-default-text" ).removeClass( "ui-input-default-hidden" );
+ }
+ } );
}
- return { x : newleft, y : newtop };
+ if ( !input.attr("placeholder") ) {
+ input.attr( "placeholder", "Search" );
+ }
},
- _setPosition: function ( x_where, y_where ) {
- var x = ( undefined === x_where ? $( window ).width() / 2 : x_where ),
- y = ( undefined === y_where ? $( window ).height() / 2 : y_where ),
- coords,
- ctxpopup = this.element.data("ctxpopup"),
- popupWidth,
- menuHeight,
- menuWidth,
- screenHeight,
- screenWidth,
- roomtop,
- roombot,
- halfheight,
- maxwidth,
- newtop,
- newleft;
+ disable: function () {
+ this.element.attr( "disabled", true );
+ this.element.parent().addClass( "ui-disabled" );
+ $( this.element ).blur();
+ this.element.parent().parent().find(".ui-input-cancel").addClass( "ui-disabled" );
+ },
- if ( !ctxpopup ) {
- popupWidth = $( window ).width() * this.options.widthRatio;
- this._ui.container.css( "width", popupWidth );
+ enable: function () {
+ this.element.attr( "disabled", false );
+ this.element.parent().removeClass( "ui-disabled" );
+ this.element.parent().parent().find(".ui-input-cancel").removeClass( "ui-disabled" );
+ $( this.element ).focus();
+ }
+ } );
- if ( this._ui.container.outerWidth() > $( window ).width() ) {
- this._ui.container.css( {"max-width" : $( window ).width() - 30} );
- }
- }
+ //auto self-init widgets
+ $( document ).bind( "pagecreate create", function ( e ) {
+ $.tizen.searchbar.prototype.enhanceWithin( e.target );
+ } );
- coords = this._placementCoords( x, y,
- this._ui.container.outerWidth(),
- this._ui.container.outerHeight() );
+}( jQuery ) );
- menuHeight = this._ui.container.innerHeight();
- menuWidth = this._ui.container.innerWidth();
- screenHeight = $( window ).height();
- screenWidth = $( window ).width();
- roomtop = y;
- roombot = screenHeight - y;
- halfheight = menuHeight / 2;
- maxwidth = parseFloat( this._ui.container.css( "max-width" ) );
- newtop = ( screenHeight - menuHeight ) / 2;
- if ( !maxwidth || menuWidth < maxwidth ) {
- newleft = ( screenWidth - menuWidth ) / 2;
- } else {
- newleft = x - menuWidth / 2;
- if ( newleft < 30 ) {
- newleft = 30;
- } else if ( ( newleft + menuWidth ) > screenWidth ) {
- newleft = screenWidth - menuWidth - 30;
- }
- }
+/* ***************************************************************************
+ * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ * ***************************************************************************
+ *
+ * jQuery Mobile Framework : "tabbar" plugin
+ * Copyright (c) jQuery Project
+ * Dual licensed under the MIT or GPL Version 2 licenses.
+ * http://jquery.org/license
+ * Authors: Jinhyuk Jun <jinhyuk.jun@samsung.com>
+*/
- if ( ctxpopup ) {
- newtop = coords.y;
- newleft = coords.x;
- }
+/**
+ * Tabbar can be created using data-role = "tabbar" inside footer
+ * Framework determine which tabbar will display with tabbar attribute
+ *
+ * Examples:
+ *
+ * HTML markup for creating tabbar: ( 2 ~ 5 li item available )
+ * icon can be changed data-icon attribute (customized icon need)
+ * <div data-role="footer" data-position ="fixed">
+ * <div data-role="tabbar">
+ * <ul>
+ * <li><a href="#" class="ui-btn-active">Menu</a></li>
+ * <li><a href="#">Save</a></li>
+ * <li><a href="#">Share</a></li>
+ * </ul>
+ * </div>
+ * </div>
+*/
- this._ui.container.css({
- top: newtop,
- left: newleft
- });
+(function ( $, undefined ) {
- this._ui.screen.css( "height", screenHeight );
+ $.widget( "tizen.tabbar", $.mobile.widget, {
+ options: {
+ iconpos: "top",
+ grid: null,
+ defaultList : 4,
+ initSelector: ":jqmData(role='tabbar')"
},
- open: function ( x_where, y_where, backgroundclose ) {
- var self = this,
- zIndexMax = 0;
-
- if ( this._isOpen || this.options.disabled ) {
- return;
- }
- $( document ).find("*").each( function () {
- var el = $( this ),
- zIndex = parseInt( el.css("z-index"), 10 );
+ _create: function () {
- if ( !( el.is( self._ui.container ) ||
- el.is( self._ui.screen ) ||
- isNaN( zIndex ))) {
- zIndexMax = Math.max( zIndexMax, zIndex );
- }
- } );
+ var $tabbar = this.element,
+ $tabbtns,
+ textpos,
+ iconpos,
+ theme = $.mobile.listview.prototype.options.theme, /* Get current theme */
+ ww = window.innerWidth || $( window ).width(),
+ wh = window.innerHeight || $( window ).height(),
+ tabbarDividerLeft = "<div class='ui-tabbar-divider ui-tabbar-divider-left'></div>",
+ tabbarDividerRight = "<div class='ui-tabbar-divider ui-tabbar-divider-right'></div>",
+ isLandscape;
- this._ui.screen.css( "height", $( window ).height() );
+ isLandscape = ww > wh && ( ww - wh );
- if ( backgroundclose ) {
- this._ui.screen.css( "opacity", 0 )
- .removeClass("ui-screen-hidden");
+ if ( isLandscape ) {
+ $tabbar.removeClass( "ui-portrait-tabbar" ).addClass( "ui-landscape-tabbar" );
} else {
- this._ui.removeClass("ui-screen-hidden");
-
- if ( this.options.fade ) {
- this._ui.screen.animate( {opacity: this.options.opacity}, "fast" );
- } else {
- this._ui.screen.css( {opacity: this.options.opacity} );
- }
+ $tabbar.removeClass( "ui-landscape-tabbar" ).addClass( "ui-portrait-tabbar" );
}
- this._setPosition( x_where, y_where );
-
- this.element.trigger("popupbeforeposition");
-
- this._ui.container
- .removeClass("ui-selectmenu-hidden")
- .addClass("in")
- .animationComplete( function () {
- self.element.trigger("popupafteropen");
- } );
+ if ( $tabbar.find( "a" ).length ) {
+ $tabbtns = $tabbar.find( "a" );
+ iconpos = $tabbtns.filter( ":jqmData(icon)" ).length ? this.options.iconpos : undefined;
+ textpos = $tabbtns.html().length ? true : false;
+ }
- this._isOpen = true;
+ if ( $tabbar.parents( ".ui-header" ).length && $tabbar.parents( ".ui-scrollview-view" ).length ) {
+ $tabbar.find( "li" ).addClass( "tabbar-scroll-li" );
+ $tabbar.find( "ul" ).addClass( "tabbar-scroll-ul" );
- if ( !this._reflow ) {
- this._reflow = function () {
- if ( !self._isOpen ) {
- return;
- }
+ /* add shadow divider */
+ $( tabbarDividerLeft ).appendTo( $tabbar.parents( ".ui-scrollview-clip" ) );
+ $( tabbarDividerRight ).appendTo( $tabbar.parents( ".ui-scrollview-clip" ) );
- self._setPosition( x_where, y_where );
- };
+ $( ".ui-tabbar-divider-left" ).hide();
+ $( ".ui-tabbar-divider-right" ).hide();
- $( window ).bind( "resize", this._reflow );
+ /* add width calculation*/
+ if ( $tabbar.parents( ".ui-scrollview-view" ).data("default-list") ) {
+ this.options.defaultList = $tabbar.parents( ".ui-scrollview-view" ).data( "default-list" );
+ }
+ $tabbar.find( "li" ).css( "width", window.innerWidth / this.options.defaultList + "px" );
+ } else {
+ if ( $tabbar.find( "ul" ).children().length ) {
+ $tabbar.addClass( "ui-navbar" )
+ .find( "ul" )
+ .grid( { grid: this.options.grid } );
+ }
}
- },
- close: function () {
- if ( !this._isOpen ) {
- return;
+ if ( $tabbar.parents( ".ui-footer" ).length ) {
+ $tabbar.find( "li" ).addClass( "ui-tab-btn-style" );
}
- if ( this._reflow ) {
- $( window ).unbind( "resize", this._reflow );
- this._reflow = null;
+ /* title tabbar */
+ if ( $tabbar.siblings( ".ui-title" ).length ) {
+ $tabbar.parents( ".ui-header" ).addClass( "ui-title-tabbar" );
}
- var self = this,
- hideScreen = function () {
- self._ui.screen.addClass("ui-screen-hidden");
- self._isOpen = false;
- };
-
- this._ui.container.removeClass("in").addClass("reverse out");
+ if ( !iconpos ) {
+ $tabbar.addClass( "ui-tabbar-noicons" );
+ }
+ if ( !textpos ) {
+ $tabbar.addClass( "ui-tabbar-notext" );
+ }
+ if ( textpos && iconpos ) {
+ $tabbar.parents( ".ui-header" ).addClass( "ui-title-tabbar-multiline" );
+ }
- if ( this.options.transition === "none" ) {
- this._ui.container
- .addClass("ui-selectmenu-hidden")
- .removeAttr("style");
- this.element.trigger("popupafterclose");
- } else {
- this._ui.container.animationComplete( function () {
- self._ui.container
- .removeClass("reverse out")
- .addClass("ui-selectmenu-hidden")
- .removeAttr("style");
- self.element.trigger("popupafterclose");
- } );
+ if ( $tabbar.find( "a" ).length ) {
+ $tabbtns.buttonMarkup({
+ corners: false,
+ shadow: false,
+ iconpos: iconpos
+ });
}
- if ( this.options.fade ) {
- this._ui.screen.animate( {opacity: 0}, "fast", hideScreen );
- } else {
- hideScreen();
+ if ( $tabbar.find( ".ui-state-persist" ).length ) {
+ $tabbar.addClass( "ui-tabbar-persist" );
}
- },
- _realSetTheme: function ( dst, theme ) {
- var classes = ( dst.attr("class") || "" ).split(" "),
- alreadyAdded = true,
- currentTheme = null,
- matches;
+ $tabbar.delegate( "a", "vclick", function ( event ) {
+ $tabbtns.not( ".ui-state-persist" ).removeClass( $.mobile.activeBtnClass );
+ $( this ).addClass( $.mobile.activeBtnClass );
+ });
- while ( classes.length > 0 ) {
- currentTheme = classes.pop();
- matches = currentTheme.match(/^ui-body-([a-z])$/);
+ $tabbar.addClass( "ui-tabbar");
- if ( matches && matches.length > 1 ) {
- currentTheme = matches[1];
- break;
- } else {
- currentTheme = null;
+ $( document ).bind( "pagebeforeshow", function ( event, ui ) {
+ var footer_filter = $( event.target ).find( ":jqmData(role='footer')" ),
+ tabbar_filter = footer_filter.find( ":jqmData(role='tabbar')" ),
+ $elFooterMore = tabbar_filter.siblings( ":jqmData(icon='naviframe-more')" ),
+ $elFooterBack = tabbar_filter.siblings( ".ui-btn-back" );
+
+ footer_filter
+ .css( "position", "fixed" )
+ .css( "bottom", 0 )
+ .css( "height", tabbar_filter.height() );
+ if ( $elFooterMore.length ) {
+ tabbar_filter.addClass( "ui-tabbar-margin-more" );
}
- }
+ if ( $elFooterBack.length ) {
+ tabbar_filter.addClass( "ui-tabbar-margin-back" );
+ }
+ });
- dst.removeClass( "ui-body-" + currentTheme );
- if ( ( theme || "" ).match(/[a-z]/) ) {
- dst.addClass( "ui-body-" + theme );
- }
- },
+ $tabbar.bind( "touchstart vmousedown", function ( e ) {
+ var $tabbarScroll = $( e.target ).parents( ".ui-scrollview-view" );
+ if ( $tabbarScroll.offset() ) {
+ if ( $tabbarScroll.offset().left < 0 ) {
+ $( ".ui-tabbar-divider-left" ).show();
+ } else {
+ $( ".ui-tabbar-divider-left" ).hide();
+ }
+ if ( ( $tabbarScroll.width() - $tabbarScroll.parents( ".ui-scrollview-clip" ).width() ) == Math.abs( $tabbarScroll.offset().left ) ) {
+ $( ".ui-tabbar-divider-right" ).hide();
+ } else {
+ $( ".ui-tabbar-divider-right" ).show();
+ }
+ }
+ });
- _setTheme: function ( value ) {
- this._realSetTheme( this.element, value );
- this.options.theme = value;
- this.element.attr( "data-" + ( $.mobile.ns || "" ) + "theme", value );
+ this._bindTabbarEvents();
+ this._initTabbarAnimation();
},
- _setOverlayTheme: function ( value ) {
- this._realSetTheme( this._ui.container, value );
- this.options.overlayTheme = value;
- this.element.attr( "data-" + ( $.mobile.ns || "" ) + "overlay-theme", value );
- },
+ _initTabbarAnimation: function () {
+ var isScrollingStart = false,
+ isScrollingEnd = false;
+ $( document ).bind( "scrollstart.tabbar", function ( e ) {
+ if ( $( e.target ).find( ".ui-tabbar" ).length ) {
+ isScrollingStart = true;
+ isScrollingEnd = false;
+ }
+ });
- _setShadow: function ( value ) {
- this.options.shadow = value;
- this.element.attr( "data-" + ( $.mobile.ns || "" ) + "shadow", value );
- this._ui.container[value ? "addClass" : "removeClass"]("ui-overlay-shadow");
- },
+ $( document ).bind( "scrollstop.tabbar", function ( e ) {
+ var $tabbarScrollview = $( e.target ),
+ $elTabbar = $( e.target ).find( ".ui-tabbar" ),
+ $elTabbarLI = $( e.target ).find( ".ui-tabbar li" ),
+ $minElement = $elTabbarLI.eq( 0 ),
+ minElementIndexVal,
+ minElementIndex = -1;
- _setCorners: function ( value ) {
- this.options.corners = value;
- this.element.attr( "data-" + ( $.mobile.ns || "" ) + "corners", value );
- this._ui.container[value ? "addClass" : "removeClass"]("ui-corner-all");
- },
+ isScrollingEnd = true;
+ if ( $elTabbar.length && isScrollingStart == true ) {
+ minElementIndexVal = Math.abs( $elTabbarLI.eq( 0 ).offset().left );
+ $elTabbarLI.each( function ( i ) {
+ var offset = $elTabbarLI.eq( i ).offset();
- _setFade: function ( value ) {
- this.options.fade = value;
- this.element.attr( "data-" + ( $.mobile.ns || "" ) + "fade", value );
- },
+ if ( Math.abs( offset.left ) < minElementIndexVal ) {
+ minElementIndexVal = Math.abs( offset.left );
+ minElementIndex = i;
+ $minElement = $elTabbarLI.eq( i );
+ }
+ });
- _setTransition: function ( value ) {
- this._ui.container
- .removeClass( this.options.transition || "" )
- .addClass( value );
- this.options.transition = value;
- this.element.attr( "data-" + ( $.mobile.ns || "" ) + "transition", value );
+ if ( $tabbarScrollview.length && isScrollingStart == isScrollingEnd && minElementIndex != -1) {
+ isScrollingStart = false;
+ $tabbarScrollview.scrollview( "scrollTo", -( window.innerWidth / $elTabbar.data( "defaultList" ) * minElementIndex ) , 0, 357);
+ }
+ }
+
+ $( ".ui-tabbar-divider-left" ).hide();
+ $( ".ui-tabbar-divider-right" ).hide();
+ });
},
- _setDisabled: function ( value ) {
- $.Widget.prototype._setOption.call( this, "disabled", value );
- if ( value ) {
- this.close();
- }
- }
- });
+ _bindTabbarEvents: function () {
+ var $tabbar = this.element;
- $.tizen.popupwindow.bindPopupToButton = function ( btn, popup ) {
- if ( btn.length === 0 || popup.length === 0 ) {
- return;
- }
+ $( window ).bind( "orientationchange", function ( e, ui ) {
+ var ww = window.innerWidth || $( window ).width(),
+ wh = window.innerHeight || $( window ).height(),
+ isLandscape = ww > wh && ( ww - wh );
- var btnVClickHandler = function ( e ) {
- if ( !popup.jqmData("overlay-theme-set") ) {
- popup.popupwindow( "option", "overlayTheme", btn.jqmData("theme") );
- }
+ if ( isLandscape ) {
+ $tabbar.removeClass( "ui-portrait-tabbar" ).addClass( "ui-landscape-tabbar" );
+ } else {
+ $tabbar.removeClass( "ui-landscape-tabbar" ).addClass( "ui-portrait-tabbar" );
+ }
+ });
+ },
- popup.popupwindow( "open",
- btn.offset().left + btn.outerWidth() / 2,
- btn.offset().top + btn.outerHeight() / 2 );
+ _setDisabled: function ( value, cnt ) {
+ this.element.find( "li" ).eq( cnt ).attr( "disabled", value );
+ this.element.find( "li" ).eq( cnt ).attr( "aria-disabled", value );
+ },
- return false;
- };
+ disable: function ( cnt ) {
+ this._setDisabled( true, cnt );
+ this.element.find( "li" ).eq( cnt ).addClass( "ui-disabled" );
+ },
- if ( ( popup.popupwindow("option", "overlayTheme") || "" ).match(/[a-z]/) ) {
- popup.jqmData( "overlay-theme-set", true );
+ enable: function ( cnt ) {
+ this._setDisabled( false, cnt );
+ this.element.find( "li" ).eq( cnt ).removeClass( "ui-disabled" );
}
+ });
- btn
- .attr({
- "aria-haspopup": true,
- "aria-owns": btn.attr("href")
- })
- .removeAttr("href")
- .bind( "vclick", btnVClickHandler );
-
- popup.bind( "destroyed", function () {
- btn.unbind( "vclick", btnVClickHandler );
- } );
- };
-
+ //auto self-init widgets
$( document ).bind( "pagecreate create", function ( e ) {
- $( $.tizen.popupwindow.prototype.options.initSelector, e.target )
- .not(":jqmData(role='none'), :jqmData(role='nojs')")
- .popupwindow();
-
- $( "a[href^='#']:jqmData(rel='popupwindow')", e.target ).each( function () {
- $.tizen.popupwindow.bindPopupToButton( $( this ), $( $( this ).attr("href") ) );
- });
+ $( $.tizen.tabbar.prototype.options.initSelector, e.target ).tabbar();
});
-}( jQuery ));
+}( jQuery ) );
} ( jQuery, this ) );
-(function($){$.tizen.frameworkData.pkgVersion="0.2.26";}(jQuery));
+(function($){$.tizen.frameworkData.pkgVersion="0.2.27";}(jQuery));
****************************************************************************
Flora License
-Version 1.0, April, 2013
+Version 1.1, April, 2013
http://floralicense.org/license/
Copyright [yyyy] [name of copyright owner]
- Licensed under the Flora License, Version 1.0 (the "License");
+ Licensed under the Flora License, Version 1.1 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
glMatrix 1.3.7 (https://github.com/toji/gl-matrix) [https://github.com/toji/gl-matrix/blob/master/LICENSE.md]
*/
-function range(a,b,c){var d=[],e,f,g,h=c||1,i=!1;!isNaN(a)&&!isNaN(b)?(e=a,f=b):isNaN(a)&&isNaN(b)?(i=!0,e=a.charCodeAt(0),f=b.charCodeAt(0)):(e=isNaN(a)?0:a,f=isNaN(b)?0:b),g=e>f?!1:!0;if(g)while(e<=f)d.push(i?String.fromCharCode(e):e),e+=h;else while(e>=f)d.push(i?String.fromCharCode(e):e),e-=h;return d}(function(a,b,c,d){function e(c){var d=a(c),e=d.children(".ui-content"),f=d.children(".ui-header").outerHeight()||0,g=d.children(".ui-footer").outerHeight()||0,h=parseFloat(e.css("padding-top")),i=parseFloat(e.css("padding-bottom")),j=a(b).height();e.height(j-(f+g)-(h+i))}function f(b){this.options=a.extend({},b),this.easing="easeOutQuad",this.reset()}function h(){return Date.now()}var g={scrolling:0,overshot:1,snapback:2,done:3};jQuery.widget("tizen.scrollview",jQuery.mobile.widget,{options:{direction:null,timerInterval:10,scrollDuration:1e3,overshootDuration:250,snapbackDuration:500,moveThreshold:30,moveIntervalThreshold:150,scrollMethod:"translate",startEventName:"scrollstart",updateEventName:"scrollupdate",stopEventName:"scrollstop",eventType:a.support.touch?"touch":"mouse",showScrollBars:!0,overshootEnable:!1,outerScrollEnable:!1,overflowEnable:!0,scrollJump:!1},_getViewHeight:function(){return this._$view.height()},_getViewWidth:function(){return this._$view.width()},_makePositioned:function(a){a.css("position")==="static"&&a.css("position","relative")},_create:function(){var b,c=this;this._$clip=a(this.element).addClass("ui-scrollview-clip"),this._$clip.children(".ui-scrollview-view").length?this._$view=this._$clip.children(".ui-scrollview-view"):this._$view=this._$clip.wrapInner("<div></div>").children().addClass("ui-scrollview-view"),this.options.scrollMethod==="translate"&&this._$view.css("transform")===d&&(this.options.scrollMethod="position"),this._$clip.css("overflow","hidden"),this._makePositioned(this._$clip),this._makePositioned(this._$view),this._$view.css({left:0,top:0}),this._view_height=this._getViewHeight(),this._sx=0,this._sy=0,b=this.options.direction,this._hTracker=b!=="y"?new f(this.options):null,this._vTracker=b!=="x"?new f(this.options):null,this._timerInterval=this.options.timerInterval,this._timerID=0,this._timerCB=function(){c._handleMomentumScroll()},this._add_event(),this._add_scrollbar(),this._add_scroll_jump(),this._add_overflow_indicator()},_startMScroll:function(a,b){var c=!1,d=this.options.scrollDuration,e=this._hTracker,f=this._vTracker,g,h;this._$clip.trigger(this.options.startEventName);if(e){g=this._$clip.width(),h=this._getViewWidth();if((this._sx===0&&a>0||this._sx===-(h-g)&&a<0)&&h>g)return;e.start(this._sx,a,d,h>g?-(h-g):0,0),c=!e.done()}if(f){g=this._$clip.height(),h=this._getViewHeight();if((this._sy===0&&b>0||this._sy===-(h-g)&&b<0)&&h>g)return;f.start(this._sy,b,d,h>g?-(h-g):0,0),c=c||!f.done()}c?this._timerID=setTimeout(this._timerCB,this._timerInterval):this._stopMScroll()},_stopMScroll:function(){this._timerID&&(this._$clip.trigger(this.options.stopEventName),clearTimeout(this._timerID)),this._timerID=0,this._vTracker&&this._vTracker.reset(),this._hTracker&&this._hTracker.reset(),this._hideScrollBars(),this._hideOverflowIndicator()},_handleMomentumScroll:function(){var a=!1,b=0,c=0,d=0,e=this,f=this._vTracker,g=this._hTracker;if(this._outerScrolling)return;f&&(f.update(this.options.overshootEnable),c=f.getPosition(),a=!f.done(),f.getRemained()>this.options.overshootDuration&&(d=this._getViewHeight()-this._$clip.height(),f.isAvail()?f.isMin()?this._outerScroll(c-f.getRemained()/3,d):f.isMax()&&this._outerScroll(f.getRemained()/3,d):this._speedY>0?this._outerScroll(f.getRemained()/3,d):this._outerScroll(c-f.getRemained()/3,d))),g&&(g.update(this.options.overshootEnable),b=g.getPosition(),a=a||!g.done()),this._setScrollPosition(b,c),this._$clip.trigger(this.options.updateEventName,[{x:b,y:c}]),a?this._timerID=setTimeout(this._timerCB,this._timerInterval):this._stopMScroll()},_setElementTransform:function(b,c,e,f){var g,h;!f||f===d?h="none":h="-webkit-transform "+f/1e3+"s ease-out",a.support.cssTransform3d?g="translate3d("+c+","+e+", 0px)":g="translate("+c+","+e+")",b.css({"-moz-transform":g,"-webkit-transform":g,"-ms-transform":g,"-o-transform":g,transform:g,"-webkit-transition":h})},_setEndEffect:function(a){var b=this._getViewHeight()-this._$clip.height();if(this._softkeyboard){this._effect_dir?this._outerScroll(-b-this._softkeyboardHeight,b):this._outerScroll(this._softkeyboardHeight,b);return}if(a==="in"){if(this._endEffect)return;this._endEffect=!0,this._setOverflowIndicator(this._effect_dir),this._showOverflowIndicator()}else if(a==="out"){if(!this._endEffect)return;this._endEffect=!1}else this._endEffect=!1,this._setOverflowIndicator(),this._showOverflowIndicator()},_setCalibration:function(a,b){if(this.options.overshootEnable){this._sx=a,this._sy=b;return}var c=this._$view,d=this._$clip,e=this._directionLock,f=0,g=0;e!=="y"&&this._hTracker&&(g=c.width()-d.width(),a>=0?this._sx=0:a<-g?this._sx=-g:this._sx=a,g<0&&(this._sx=0)),e!=="x"&&this._vTracker&&(f=this._getViewHeight()-d.height(),b>0?(this._sy=0,this._effect_dir=0,this._setEndEffect("in")):b<-f?(this._sy=-f,this._effect_dir=1,this._setEndEffect("in")):(this._endEffect&&this._sy!==b&&this._setEndEffect(),this._sy=b),f<0&&(this._sy=0))},_setScrollPosition:function(a,b,c){var d=this._$view,e=this.options.scrollMethod,f=this._$vScrollBar,g=this._$hScrollBar,h;this._setCalibration(a,b),a=this._sx,b=this._sy,e==="translate"?this._setElementTransform(d,a+"px",b+"px",c):d.css({left:a+"px",top:b+"px"}),f&&(h=f.find(".ui-scrollbar-thumb"),e==="translate"?this._setElementTransform(h,"0px",-b/this._getViewHeight()*h.parent().height()+"px",c):h.css("top",-b/this._getViewHeight()*100+"%")),g&&(h=g.find(".ui-scrollbar-thumb"),e==="translate"?this._setElementTransform(h,-a/d.width()*h.parent().width()+"px","0px",c):h.css("left",-a/d.width()*100+"%"))},_outerScroll:function(c,e){var f=this,g=a(b).scrollTop()-b.screenTop,i=0,j=this.options.snapbackDuration,k=h(),l;if(!this.options.outerScrollEnable)return;if(this._$clip.jqmData("scroll")!=="y")return;if(this._outerScrolling)return;if(c>0)i=b.screenTop?b.screenTop:-c;else{if(!(c<-e))return;i=-c-e}l=function(){var c=h()-k;c>=j?(b.scrollTo(0,g+i),f._outerScrolling=d,f._stopMScroll()):(ec=a.easing.easeOutQuad(c/j,c,0,1,j),b.scrollTo(0,g+i*ec),f._outerScrolling=setTimeout(l,f._timerInterval))},this._outerScrolling=setTimeout(l,f._timerInterval)},_scrollTo:function(b,c,d){var e=this,f=h(),g=a.easing.easeOutQuad,i=this._sx,j=this._sy,k=b-i,l=c-j,m;b=-b,c=-c,m=function(){var a=h()-f,n;a>=d?(e._timerID=0,e._setScrollPosition(b,c)):(n=g(a/d,a,0,1,d),e._setScrollPosition(i+k*n,j+l*n),e._timerID=setTimeout(m,e._timerInterval))},this._timerID=setTimeout(m,this._timerInterval)},scrollTo:function(a,b,c){this._stopMScroll(),this._didDrag=!1,!c||this.options.scrollMethod==="translate"?this._setScrollPosition(a,b,c):this._scrollTo(a,b,c)},getScrollPosition:function(){return{x:-this._sx,y:-this._sy}},skipDragging:function(a){this._skip_dragging=a},_getScrollHierarchy:function(){var b=[],c;return this._$clip.parents(".ui-scrollview-clip").each(function(){c=a(this).jqmData("scrollview"),c&&b.unshift(c)}),b},_getAncestorByDirection:function(a){var b=this._getScrollHierarchy(),c=b.length,d,e;while(0<c--){d=b[c],e=d.options.direction;if(!e||e===a)return d}return null},_handleDragStart:function(b,c,d){this._stopMScroll(),this._didDrag=!1,this._skip_dragging=!1;var e=a(b.target),f=this,g=this._$clip,h=this.options.direction;this._is_button=e.is(".ui-btn")||e.is(".ui-btn-text")||e.is(".ui-btn-inner")||e.is(".ui-btn-inner .ui-icon");if(e.parents(".ui-slider").length||e.is(".ui-slider")){this._skip_dragging=!0;return}e.is("textarea")&&e.bind("scroll",function(){f._skip_dragging=!0,e.unbind("scroll")}),this._is_inputbox=e.is(":input")||e.parents(":input").length>0,this._is_inputbox&&e.one("resize.scrollview",function(){d>g.height()&&f.scrollTo(-c,f._sy-d+g.height(),f.options.snapbackDuration)}),this.options.eventType==="mouse"&&!this._is_inputbox&&!this._is_button&&b.preventDefault(),this._lastX=c,this._lastY=d,this._startY=d,this._doSnapBackX=!1,this._doSnapBackY=!1,this._speedX=0,this._speedY=0,this._directionLock="",this._lastMove=0,this._enableTracking(),this._set_scrollbar_size()},_propagateDragMove:function(a,b,c,d,e){this._hideScrollBars(),this._hideOverflowIndicator(),this._disableTracking(),a._handleDragStart(b,c,d),a._directionLock=e,a._didDrag=this._didDrag},_handleDragMove:function(b,c,d){if(this._skip_dragging)return;if(!this._dragging)return;!this._is_inputbox&&!this._is_button&&b.preventDefault();var e=this.options.moveThreshold,f=c-this._lastX,g=d-this._lastY,i=this.options.direction,j=null,k,l,m,n,o,p,q;this._lastMove=h();if(!this._directionLock){k=Math.abs(f),l=Math.abs(g);if(k<e&&l<e)return!1;k<l&&k/l<.5?j="y":k>l&&l/k<.5&&(j="x");if(i&&j&&i!==j){m=this._getAncestorByDirection(j);if(m)return this._propagateDragMove(m,b,c,d,j),!1}this._directionLock=i||j||"none"}o=this._sx,p=this._sy,q=this._directionLock;if(q!=="y"&&this._hTracker){k=this._sx,this._speedX=f,o=k+f,this._doSnapBackX=!1,n=o>0||o<this._maxX;if(n&&q==="x"){m=this._getAncestorByDirection("x");if(m)return this._setScrollPosition(o>0?0:this._maxX,p),this._propagateDragMove(m,b,c,d,j),!1;o=k+f/2,this._doSnapBackX=!0}}if(q!=="x"&&this._vTracker){if(Math.abs(this._startY-d)<e&&q!=="xy")return;l=this._sy,this._speedY=g,p=l+g,this._doSnapBackY=!1,n=p>0||p<this._maxY;if(n&&q==="y"){m=this._getAncestorByDirection("y");if(m)return this._setScrollPosition(o,p>0?0:this._maxY),this._propagateDragMove(m,b,c,d,j),!1;p=l+g/2,this._doSnapBackY=!0}}this.options.overshootEnable===!1&&(this._doSnapBackX=!1,this._doSnapBackY=!1),this._lastX=c,this._lastY=d,this._setScrollPosition(o,p),this._didDrag===!1&&(this._didDrag=!0,this._showScrollBars(),this._showOverflowIndicator(),this._$clip.parents(".ui-scrollview-clip").each(function(){a(this).scrollview("skipDragging",!0)}))},_handleDragStop:function(a){var b=this;if(this._skip_dragging)return;var c=this._lastMove,d=h(),e=c&&d-c<=this.options.moveIntervalThreshold,f=this._hTracker&&this._speedX&&e?this._speedX:this._doSnapBackX?1:0,g=this._vTracker&&this._speedY&&e?this._speedY:this._doSnapBackY?1:0,i=this.options.direction,j,k;return f||g?this._setGestureScroll(f,g)||this._startMScroll(f,g):(this._hideScrollBars(),this._hideOverflowIndicator()),this._disableTracking(),this._endEffect&&setTimeout(function(){b._setEndEffect("out"),b._hideScrollBars(),b._hideOverflowIndicator()},300),!this._didDrag},_setGestureScroll:function(a,b){var c=this,e=function(){clearTimeout(c._gesture_timer),c._gesture_dir=0,c._gesture_timer=d},f={top:0,bottom:1,left:2,right:3};return!b&&!a?!1:(Math.abs(a)>Math.abs(b)?dir=a>0?f.left:f.right:dir=b>0?f.top:f.bottom,this._gesture_timer?this._gesture_dir!==dir?(e(),!1):!1:(this._gesture_dir=dir,this._gesture_timer=setTimeout(function(){e()},1e3),!1))},_enableTracking:function(){this._dragging=!0},_disableTracking:function(){this._dragging=!1},_showScrollBars:function(a){var b="ui-scrollbar-visible",c=this;if(!this.options.showScrollBars)return;if(this._scrollbar_showed)return;this._$vScrollBar&&this._$vScrollBar.addClass(b),this._$hScrollBar&&this._$hScrollBar.addClass(b),this._scrollbar_showed=!0,a&&setTimeout(function(){c._hideScrollBars()},a)},_hideScrollBars:function(){var a="ui-scrollbar-visible";if(!this.options.showScrollBars)return;if(!this._scrollbar_showed)return;this._$vScrollBar&&this._$vScrollBar.removeClass(a),this._$hScrollBar&&this._$hScrollBar.removeClass(a),this._scrollbar_showed=!1},_setOverflowIndicator:function(a){a===1?(this._opacity_top="0",this._opacity_bottom="0.8"):a===0?(this._opacity_top="0.8",this._opacity_bottom="0"):(this._opacity_top="0.5",this._opacity_bottom="0.5")},_showOverflowIndicator:function(){if(!this.options.overflowEnable||!this._overflowAvail||this._softkeyboard)return;this._overflow_top.animate({opacity:this._opacity_top},300),this._overflow_bottom.animate({opacity:this._opacity_bottom},300),this._overflow_showed=!0},_hideOverflowIndicator:function(){if(!this.options.overflowEnable||!this._overflowAvail||this._softkeyboard)return;if(this._overflow_showed===!1)return;this._overflow_top.animate({opacity:0},300),this._overflow_bottom.animate({opacity:0},300),this._overflow_showed=!1,this._setOverflowIndicator()},_add_event:function(){var c=this,e=this._$clip,f=this._$view;this.options.eventType==="mouse"?(this._dragEvt="mousedown mousemove mouseup click mousewheel",this._dragCB=function(a){switch(a.type){case"mousedown":return c._handleDragStart(a,a.clientX,a.clientY);case"mousemove":return c._handleDragMove(a,a.clientX,a.clientY);case"mouseup":return c._handleDragStop(a);case"click":return!c._didDrag;case"mousewheel":var b=c.getScrollPosition();c.scrollTo(-b.x,-(b.y-a.originalEvent.wheelDelta))}}):(this._dragEvt="touchstart touchmove touchend click",this._dragCB=function(a){var b=a.originalEvent.touches;switch(a.type){case"touchstart":if(b.length!=1)return;return c._handleDragStart(a,b[0].pageX,b[0].pageY);case"touchmove":if(b.length!=1)return;return c._handleDragMove(a,b[0].pageX,b[0].pageY);case"touchend":if(b.length!=0)return;return c._handleDragStop(a);case"click":return!c._didDrag}}),f.bind(this._dragEvt,this._dragCB),f.bind("keydown",function(f){var g,h,i=a(b).scrollTop()-b.screenTop,j;if(f.keyCode==9)return!1;g=e.find(".ui-focus");if(g===d)return;h=g.offset().top-i,j=e.offset().top+e.height()-g.height(),c._softkeyboard&&(j-=c._softkeyboardHeight),(h<e.offset().top||h>j)&&c.scrollTo(0,c._sy-(h-e.offset().top-g.height()));return}),f.bind("keyup",function(d){var f,g,h,j=a(b).scrollTop()-b.screenTop,k;if(d.keyCode!=9)return;f=a(this).find(":input");for(i=0;i<f.length;i++){if(!a(f[i]).hasClass("ui-focus"))continue;i+1==f.length?g=a(f[0]):g=a(f[i+1]),h=g.offset().top-j,k=e.offset().top+e.height()-g.height(),c._softkeyboard&&(k-=c._softkeyboardHeight),(h<0||h>k)&&c.scrollTo(0,c._sy-h+g.height()+e.offset().top,0),g.focus();break}return!1}),e.bind("updatelayout",function(a){var b,d,f=c._getViewHeight();if(!e.height()||!f){c.scrollTo(0,0,0);return}b=e.height()-f,d=f-c._view_height,c._view_height=f;if(d==0||d>e.height()/2)return;b>0?c.scrollTo(0,0,0):c._sy-b<=-d?c.scrollTo(0,c._sy,c.options.snapbackDuration):c._sy-b<=d+c.options.moveThreshold&&c.scrollTo(0,b,c.options.snapbackDuration)}),a(b).bind("resize",function(b){var d,f=c._getViewHeight();if(a(".ui-page-active").get(0)!==e.closest(".ui-page").get(0))return;if(!e.height()||!f)return;d=e.find(".ui-focus"),d&&d.trigger("resize.scrollview"),setTimeout(function(){c._sy<e.height()-c._getViewHeight()&&c.scrollTo(0,e.height()-c._getViewHeight(),c.options.overshootDuration)},260),c._view_height=f}),a(b).bind("vmouseout",function(d){var f=!1;if(a(".ui-page-active").get(0)!==e.closest(".ui-page").get(0))return;if(!c._dragging)return;if(d.pageX<0||d.pageX>a(b).width())f=!0;if(d.pageY<0||d.pageY>a(b).height())f=!0;f&&(c._hideScrollBars(),c._hideOverflowIndicator(),c._disableTracking())}),this._softkeyboard=!1,this._softkeyboardHeight=0,b.addEventListener("softkeyboardchange",function(d){if(a(".ui-page-active").get(0)!==e.closest(".ui-page").get(0))return;c._softkeyboard=d.state==="on"?!0:!1,c._softkeyboardHeight=parseInt(d.height)*(a(b).width()/b.screen.availWidth)}),e.closest(".ui-page").bind("pageshow",function(a){setTimeout(function(){c._view_height=c._getViewHeight(),c._set_scrollbar_size(),c._setScrollPosition(c._sx,c._sy),c._showScrollBars(2e3)},0)})},_add_scrollbar:function(){var a=this._$clip,b='<div class="ui-scrollbar ui-scrollbar-',c='"><div class="ui-scrollbar-track"><div class="ui-scrollbar-thumb"></div></div></div>';if(!this.options.showScrollBars)return;this._vTracker&&(a.append(b+"y"+c),this._$vScrollBar=a.children(".ui-scrollbar-y")),this._hTracker&&(a.append(b+"x"+c),this._$hScrollBar=a.children(".ui-scrollbar-x")),this._scrollbar_showed=!1},_add_scroll_jump:function(){var b=this._$clip,c=this,d,e;if(!this.options.scrollJump)return;this._vTracker&&(d=a('<div class="ui-scroll-jump-top-bg"><div data-role="button" data-inline="true" data-icon="scrolltop" data-style="box"></div></div>'),b.append(d).trigger("create"),d.bind("vclick",function(){c.scrollTo(0,0,c.options.overshootDuration)})),this._hTracker&&(e=a('<div class="ui-scroll-jump-left-bg"><div data-role="button" data-inline="true" data-icon="scrollleft" data-style="box"></div></div>'),b.append(e).trigger("create"),e.bind("vclick",function(){c.scrollTo(0,0,c.options.overshootDuration)}))},_add_overflow_indicator:function(){if(!this.options.overflowEnable)return;this._overflow_top=a('<div class="ui-overflow-indicator-top"></div>'),this._overflow_bottom=a('<div class="ui-overflow-indicator-bottom"></div>'),this._$clip.append(this._overflow_top),this._$clip.append(this._overflow_bottom),this._opacity_top="0.5",this._opacity_bottom="0.5",this._overflow_showed=!1},_set_scrollbar_size:function(){var a=this._$clip,b=this._$view,c=0,d=0,e=0,f=0,g;if(!this.options.showScrollBars)return;this._hTracker&&(c=a.width(),d=b.width(),this._maxX=c-d,this._maxX>0&&(this._maxX=0),this._$hScrollBar&&d&&(g=this._$hScrollBar.find(".ui-scrollbar-thumb"),g.css("width",c>=d?"0":(Math.floor(c/d*100)||1)+"%")));if(this._vTracker){e=a.height(),f=this._getViewHeight(),this._maxY=e-f;if(this._maxY>0||f===0)this._maxY=0;if(this._$vScrollBar&&f||f===0)g=this._$vScrollBar.find(".ui-scrollbar-thumb"),g.css("height",e>=f?"0":(Math.floor(e/f*100)||1)+"%"),this._overflowAvail=!!g.height()}}}),a.extend(f.prototype,{start:function(a,b,c,d,e){var f=a<d||a>e?g.snapback:g.scrolling,i;this.state=b!==0?f:g.done,this.pos=a,this.speed=b,this.duration=this.state===g.snapback?this.options.snapbackDuration:c,this.minPos=d,this.maxPos=e,this.fromPos=this.state===g.snapback?this.pos:0,i=this.pos<this.minPos?this.minPos:this.maxPos,this.toPos=this.state===g.snapback?i:0,this.startTime=h()},reset:function(){this.state=g.done,this.pos=0,this.speed=0,this.minPos=0,this.maxPos=0,this.duration=0,this.remained=0},update:function(b){var c=this.state,d=h(),e=this.duration,f=d-this.startTime,i,j,k;return c===g.done?this.pos:(f=f>e?e:f,this.remained=e-f,c===g.scrolling||c===g.overshot?(i=this.speed*(1-a.easing[this.easing](f/e,f,0,1,e)),j=this.pos+i,k=c===g.scrolling&&(j<this.minPos||j>this.maxPos),k&&(j=j<this.minPos?this.minPos:this.maxPos),this.pos=j,c===g.overshot?(b||(this.state=g.done),f>=e&&(this.state=g.snapback,this.fromPos=this.pos,this.toPos=j<this.minPos?this.minPos:this.maxPos,this.duration=this.options.snapbackDuration,this.startTime=d,f=0)):c===g.scrolling&&(k&&b?(this.state=g.overshot,this.speed=i/2,this.duration=this.options.overshootDuration,this.startTime=d):f>=e&&(this.state=g.done))):c===g.snapback&&(f>=e?(this.pos=this.toPos,this.state=g.done):this.pos=this.fromPos+(this.toPos-this.fromPos)*a.easing[this.easing](f/e,f,0,1,e)),this.pos)},done:function(){return this.state===g.done},isMin:function(){return this.pos===this.minPos},isMax:function(){return this.pos===this.maxPos},isAvail:function(){return this.minPos!==this.maxPos},getRemained:function(){return this.remained},getPosition:function(){return this.pos}}),a(c).bind("pagecreate create",function(b){var c=a(b.target),e=c.find(".ui-content").jqmData("scroll");a.support.scrollview===d&&(a.support.scrollview=!0),a.support.scrollview===!0&&e===d&&(e="y"),e!=="y"&&(e="none"),c.find(".ui-content").attr("data-scroll",e),c.find(":jqmData(scroll)").not(".ui-scrollview-clip").each(function(){if(a(this).hasClass("ui-scrolllistview"))a(this).scrolllistview();else{var b=a(this).jqmData("scroll"),c=b&&b.search(/^[xy]/)!==-1?b:null,e=a(this).hasClass("ui-content"),f;if(b==="none")return;f={direction:c||d,overflowEnable:e,scrollMethod:a(this).jqmData("scroll-method")||d,scrollJump:a(this).jqmData("scroll-jump")||d},a(this).scrollview(f)}})}),a(c).bind("pageshow",function(b){var c=a(b.target),d=c.find(".ui-content").jqmData("scroll");d==="y"&&e(b.target)})})(jQuery,window,document),function(a,b,c){a.widget("tizen.gallery",a.mobile.widget,{options:{flicking:!1,duration:500},dragging:!1,moving:!1,max_width:0,max_height:0,org_x:0,org_time:null,cur_img:null,prev_img:null,next_img:null,images:[],images_hold:[],index:0,align_type:null,direction:1,container:null,orientationEventFire:!1,_resize:function(a){var b=this.images[a],c=this.images[a].width(),d=this.images[a].height(),e=0,f,g=this.max_width-e,h=this.max_height-e;f=d/c,c>g&&(b.width(g),b.height(g*f)),d=b.height(),d>h&&(b.height(h),b.width(h/f))},_align:function(a,b){var c=this.images[a],d=0;if(!b)return;if(!b.length)return;this.align_type=="middle"?d=(this.max_height-c.height())/2:this.align_type=="bottom"?d=this.max_height-c.height():d=0,b.css("top",d+"px")},_attach:function(a,b){var d=this,e=function(){d._resize(a),d._align(a,b)},f=function(){if(d.images[a]===c)return;if(!d.images[a].height()){setTimeout(f,10);return}e()};if(!b)return;if(!b.length)return;if(a<0)return;if(!this.images.length)return;if(a>=this.images.length)return;b.css("display","block"),b.css("visibility","hidden"),b.append(this.images[a]),f()},_detach:function(a,b){if(!b)return;if(!b.length)return;if(a<0)return;if(a>=this.images.length)return;b.css("display","none"),this.images[a].removeAttr("style"),this.images[a].detach()},_detach_all:function(){var a;for(a=0;a<this.images.length;a++)this.images[a].detach()},_drag:function(a){var b,c;if(!this.dragging)return;if(this.options.flicking===!1){b=this.org_x-a;if(b<0&&!this.prev_img.length)return;if(b>0&&!this.next_img.length)return}c=a-this.org_x,this._moveLeft(this.cur_img,c+"px"),this.next_img.length&&this._moveLeft(this.next_img,c+this.window_width+"px"),this.prev_img.length&&this._moveLeft(this.prev_img,c-this.window_width+"px")},_move:function(a){var b=this.org_x-a,c=0,d,e,f;if(b==0)return;b>0?c=b<this.max_width*.45?0:1:c=-b<this.max_width*.45?0:1,c||(d=Date.now()-this.org_time,Math.abs(b)/d>1&&(c=1)),c&&(b>0&&this.next_img.length?(this._detach(this.index-1,this.prev_img),this.prev_img=this.cur_img,this.cur_img=this.next_img,this.next_img=this.next_img.next(),this.index++,this.next_img.length&&(this._moveLeft(this.next_img,this.window_width+"px"),this._attach(this.index+1,this.next_img)),this.direction=1):b<0&&this.prev_img.length&&(this._detach(this.index+1,this.next_img),this.next_img=this.cur_img,this.cur_img=this.prev_img,this.prev_img=this.prev_img.prev(),this.index--,this.prev_img.length&&(this._moveLeft(this.prev_img,-this.window_width+"px"),this._attach(this.index-1,this.prev_img)),this.direction=-1)),e=this.options.duration,f=this,this.moving=!0,setTimeout(function(){f.moving=!1},e-25),this._moveLeft(this.cur_img,"0px",e),this.next_img.length&&this._moveLeft(this.next_img,this.window_width+"px",e),this.prev_img.length&&this._moveLeft(this.prev_img,-this.window_width+"px",e)},_add_event:function(){var a=this,b;this.container.bind("vmousemove",function(b){b.preventDefault();if(a.moving)return;if(!a.dragging)return;a._drag(b.pageX)}),this.container.bind("vmousedown",function(b){b.preventDefault();if(a.moving)return;a.dragging=!0,a.org_x=b.pageX,a.org_time=Date.now()}),this.container.bind("vmouseup",function(b){if(a.moving)return;a.dragging=!1,a._move(b.pageX)}),this.container.bind("vmouseout",function(b){if(a.moving)return;if(!a.dragging)return;if(b.pageX<20||b.pageX>a.max_width-20)a._move(b.pageX),a.dragging=!1})},_del_event:function(){this.container.unbind("vmousemove"),this.container.unbind("vmousedown"),this.container.unbind("vmouseup"),this.container.unbind("vmouseout")},_setTranslateposition:function(b,c){var d,e=null,f=this;return a.support.cssTransform3d?d="translate3d("+c+", 0px, 0px)":d="translate("+c+", 0px)",e={"-moz-transform":d,"-webkit-transform":d,"-ms-transform":d,"-o-transform":d,transform:d},b.css(e),b},_hidePrevNext:function(){var a=this;a.next_img&&a.next_img.css("visibility","hidden"),a.prev_img&&a.prev_img.css("visibility","hidden")},_hideCur:function(){var a=this;a.cur_img&&a.cur_img.css("visibility","hidden")},_moveLeft:function(b,d,e){var f,g="",h=null,i=this;return a.support.cssTransform3d?f="translate3d("+d+", 0px, 0px)":f="translate("+d+", 0px)",e!==c&&(g="-webkit-transform "+e/1e3+"s ease"),h={"-moz-transform":f,"-webkit-transform":f,"-ms-transform":f,"-o-transform":f,transform:f},g!==""&&(h["-webkit-transition"]=g,d=="0px"?b.one("webkitTransitionEnd",i._hidePrevNext):b.one("webkitTransitionEnd",i._hideCur)),d=="0px"&&b.css("visibility","visible"),b.css(h),b},_show:function(){this.window_width=a(b).width(),this.max_width=this._get_width(),this.max_height=this._get_height(),this.container.css("height",this.max_height),this.cur_img=a("div").find(".ui-gallery-bg:eq("+this.index+")"),this.prev_img=this.cur_img.prev(),this.next_img=this.cur_img.next(),this._attach(this.index-1,this.prev_img),this._attach(this.index,this.cur_img),this._attach(this.index+1,this.next_img),this.cur_img.css("visibility","visible"),this.prev_img.length&&this._setTranslateposition(this.prev_img,-this.window_width+"px"),this._moveLeft(this.cur_img,"0px"),this.next_img.length&&this._setTranslateposition(this.next_img,this.window_width+"px")},show:function(){if(!this.images.length)return;this._show(),this._add_event()},_hide:function(){this._detach(this.index-1,this.prev_img),this._detach(this.index,this.cur_img),this._detach(this.index+1,this.next_img)},hide:function(){this._hide(),this._del_event()},_get_width:function(){return a(this.element).width()},_get_height:function(){var c=a(this.element).parentsUntil("ui-page"),d=c.children(".ui-content"),e=c.children(".ui-header").outerHeight()||0,f=c.children(".ui-footer").outerHeight()||0,g=parseFloat(d.css("padding-top"))+parseFloat(d.css("padding-bottom")),h=a(b).height()-e-f-g;return h},_create:function(){var c,d=this,e,f=0;a(this.element).wrapInner('<div class="ui-gallery"></div>'),a(this.element).find("img").wrap('<div class="ui-gallery-bg"></div>'),this.container=a(this.element).find(".ui-gallery"),c=a("div").find(".ui-gallery-bg:first");while(c.length)this.images[f]=c.find("img"),c=c.next(),f++;this._detach_all(),e=parseInt(a(this.element).jqmData("index"),10),e||(e=0),e<0&&(e=0),e>=this.images.length&&(e=this.images.length-1),this.index=e,this.align_type=a(this.element).jqmData("vertical-align"),a.extend(this,{_globalHandlers:[{src:a(b),handler:{orientationchange:a.proxy(this,"_orientationHandler"),resize:a.proxy(this,"_resizeHandler")}}]}),a.each(this._globalHandlers,function(a,b){b.src.bind(b.handler)})},_update:function(){var b,c,d;while(this.images_hold.length)b=this.images_hold.shift(),c=a('<div class="ui-gallery-bg"></div>'),d=a('<img src="'+b+'"></div>'),c.append(d),this.container.append(c),this.images.push(d);this._detach_all()},_resizeHandler:function(){var a=this;a.orientationEventFire&&(a.refresh(),a.orientationEventFire=!1)},_orientationHandler:function(){var a=this;a.refresh(),a.orientationEventFire=!0},refresh:function(a){return this._update(),this._hide(),a===c&&(a=this.index),a<0&&(a=0),a>=this.images.length&&(a=this.images.length-1),this.index=a,this._show(),this.index},add:function(a){this.images_hold.push(a)},remove:function(b){var d;b===c&&(b=this.index);if(b<0||b>=this.images.length)return;b==this.index?(d=this.cur_img,this.index==0?this.direction=1:this.index==this.images.length-1&&(this.direction=-1),this.direction<0?(this.cur_img=this.prev_img,this.prev_img=this.prev_img.prev(),this.prev_img.length&&(this._moveLeft(this.prev_img,-this.window_width+"px"),this._attach(b-2,this.prev_img)),this.index--):(this.cur_img=this.next_img,this.next_img=this.next_img.next(),this.next_img.length&&(this._moveLeft(this.next_img,this.window_width+"px"),this._attach(b+2,this.next_img))),this._moveLeft(this.cur_img,"0px",this.options.duration)):b==this.index-1?(d=this.prev_img,this.prev_img=this.prev_img.prev(),this.prev_img.length&&(this._moveLeft(this.prev_img,-this.window_width+"px"),this._attach(b-1,this.prev_img)),this.index--):b==this.index+1?(d=this.next_img,this.next_img=this.next_img.next(),this.next_img.length&&(this._moveLeft(this.next_img,this.window_width+"px"),this._attach(b+1,this.next_img))):d=a("div").find(".ui-gallery-bg:eq("+b+")"),this.images.splice(b,1),d.detach()},empty:function(){this.images.splice(0,this.images.length),this.container.find(".ui-gallery-bg").detach()},length:function(){return this.images.length},value:function(a){if(a===c)return this.index;this.refresh(a)},destory:function(){a(b).unbind("resize",this._resizeHandler),a(b).unbind("orientationchange",this._orientationHandler)}}),a(document).bind("pagecreate create",function(b){a(b.target).find(":jqmData(role='gallery')").gallery()}),a(document).bind("pageshow",function(b){a(b.target).find(":jqmData(role='gallery')").gallery("show")}),a(document).bind("pagebeforehide",function(b){a(b.target).find(":jqmData(role='gallery')").gallery("hide")})}(jQuery,this),function(a,b){a.widget("tizen.listdivider",a.mobile.widget,{options:{initSelector:":jqmData(role='list-divider')",folded:!1,listDividerLine:!0},_create:function(){var c=this.element,d=!0,e,f=!0,g=c.attr("data-style");c.data("line")===!1&&(this.options.listDividerLine=!1),c.data("folded")===!0&&(this.options.folded=!0);if(g==b||g==="normal"||g==="check")this.options.folded?c.buttonMarkup():c.wrapInner("<span class='ui-btn-text'></span>"),this.options.listDividerLine&&(e="<span class='ui-divider-normal-line'></span>",this.options.folded?a(e).appendTo(c.children(".ui-btn-inner")):a(e).appendTo(c));c.bind("vclick",function(a,b){})}}),a(document).bind("pagecreate create",function(b){a(a.tizen.listdivider.prototype.options.initSelector,b.target).listdivider()})}(jQuery),function(a,b,c,d){a.widget("tizen.multimediaview",a.mobile.widget,{options:{theme:null,controls:!0,fullScreen:!1,initSelector:"video, audio"},_create:function(){var b=this,c=b.element,d=c[0],e=d.nodeName==="VIDEO",f=b.options,g=a.mobile.getInheritedTheme(c,"s"),h=f.theme||g,i=d.style.getPropertyValue("width")||"",j=a("<div class='ui-multimediaview-wrap ui-multimediaview-"+h+"'>"),k=null;a.extend(this,{role:null,controlTimer:null,isVolumeHide:!0,backupView:null,_reserveVolume:-1,_isVideo:e}),c.addClass("ui-multimediaview"),k=b._createControl(),k.hide(),k.find(".ui-button").each(function(b){a(this).buttonMarkup({corners:!0,theme:h,shadow:!0})}),c.wrap(j).after(k),e?k.addClass("ui-multimediaview-video"):(b.width(i),b.options.fullScreen=!1),f.controls&&c.attr("controls")&&c.removeAttr("controls"),b._addEvent()},_resize:function(){this._resizeFullscreen(this.options.fullScreen),this._resizeControl(),this._updateSeekBar(),this._updateVolumeState()},_resizeControl:function(){var a=this,b=a.element,c=b[0],d=a._isVideo,e=b.parent(".ui-multimediaview-wrap"),f=e.find(".ui-multimediaview-control"),g=f.find(".ui-button"),h=f.find(".ui-playpausebutton"),i=f.find(".ui-seekbar"),j=f.find(".ui-durationlabel"),k=f.find(".ui-timestamplabel"),l=f.find(".ui-volumecontrol"),m=l.find(".ui-volumebar"),n=d?b.width():e.width(),o=d?b.height():f.height(),p=b.offset(),q=f.height(),r=0,s=null;f&&(d&&(s=f.offset(),s.left=p.left,s.top=p.top+o-q,f.offset(s)),f.width(n)),i&&(r=f.width()-g.outerWidth(!0)*g.length,r-=(parseInt(g.eq(0).css("margin-left"),10)+parseInt(g.eq(0).css("margin-right"),10))*g.length,a.isVolumeHide||(r-=l.outerWidth(!0)),i.width(r)),j&&!isNaN(c.duration)&&j.find("p").text(a._convertTimeFormat(c.duration)),c.autoplay&&c.paused===!1&&h.removeClass("ui-play-icon").addClass("ui-pause-icon"),i.width()<m.width()+k.width()+j.width()?j.hide():j.show()},_resizeFullscreen:function(b){if(!this._isVideo)return;var d=this,e=d.element,f=e[0],g=e.parent(".ui-multimediaview-wrap"),h=g.find(".ui-multimediaview-control"),i=h.find(".ui-fullscreenbutton"),j=a(".ui-page-active"),k=h.find(".ui-playpausebutton"),l=h.find(".ui-timestamplabel"),m=h.find(".ui-seekbar"),n=m.find(".ui-duration"),o=m.find(".ui-currenttime"),p=a("body")[0],q=j.children(".ui-header"),r=j.children(".ui-footer"),s=0,t=0;if(b)d.backupView||(d.backupView={width:f.style.getPropertyValue("width")||"",height:f.style.getPropertyValue("height")||"",position:e.css("position"),zindex:e.css("z-index"),wrapHeight:g[0].style.getPropertyValue("height")||""}),s=p.clientWidth,t=p.clientHeight-1,q.hide(),r.hide(),e.parents().each(function(b){var c=a(this);c.addClass("ui-fullscreen-parents").siblings().addClass("ui-multimediaview-siblings-off")}),i.removeClass("ui-fullscreen-on").addClass("ui-fullscreen-off"),g.height(t),e.width(s).height(t);else{if(!d.backupView)return;q.show(),r.show(),e.parents().each(function(b){var c=a(this);c.removeClass("ui-fullscreen-parents").siblings().removeClass("ui-multimediaview-siblings-off")}),i.removeClass("ui-fullscreen-off").addClass("ui-fullscreen-on"),g.css("height",d.backupView.wrapHeight),e.css({width:d.backupView.width,height:d.backupView.height,position
-:d.backupView.position,"z-index":d.backupView.zindex}),d.backupView=null,a(c).trigger("throttledresize")}},_addEvent:function(){var c=this,d=c.element,e=c.options,f=d[0],g=c._isVideo,h=d.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),i=h.find(".ui-playpausebutton"),j=h.find(".ui-timestamplabel"),k=h.find(".ui-durationlabel"),l=h.find(".ui-volumebutton"),m=h.find(".ui-volumecontrol"),n=m.find(".ui-volumebar"),o=m.find(".ui-guide"),p=m.find(".ui-handle"),q=h.find(".ui-fullscreenbutton"),r=h.find(".ui-seekbar"),s=r.find(".ui-duration"),t=r.find(".ui-currenttime"),u=a(b);d.bind("loadedmetadata.multimediaview",function(a){isNaN(f.duration)||k.find("p").text(c._convertTimeFormat(f.duration)),c._resize()}).bind("timeupdate.multimediaview",function(a){c._updateSeekBar()}).bind("play.multimediaview",function(a){i.removeClass("ui-play-icon").addClass("ui-pause-icon")}).bind("pause.multimediaview",function(a){i.removeClass("ui-pause-icon").addClass("ui-play-icon")}).bind("ended.multimediaview",function(a){(typeof f.loop=="undefined"||f.loop==="")&&c.stop()}).bind("volumechange.multimediaview",function(a){f.muted&&f.volume>.1?(l.removeClass("ui-volume-icon").addClass("ui-mute-icon"),c._reserveVolume=f.volume,f.volume=0):c._reserveVolume!==-1&&!f.muted?(l.removeClass("ui-mute-icon").addClass("ui-volume-icon"),f.volume=c._reserveVolume,c._reserveVolume=-1):f.volume<.1?l.removeClass("ui-volume-icon").addClass("ui-mute-icon"):l.removeClass("ui-mute-icon").addClass("ui-volume-icon"),c.isVolumeHide||c._updateVolumeState()}).bind("durationchange.multimediaview",function(a){isNaN(f.duration)||k.find("p").text(c._convertTimeFormat(f.duration)),c._resize()}).bind("click.multimediaview",function(a){if(!c.options.controls)return;h.fadeToggle("fast"),c._resize()}).bind("multimediaviewinit",function(a){e.controls&&h.show(),c._resize()}),i.bind("click.multimediaview",function(){c._endTimer(),f.paused?f.play():f.pause(),g&&c._startTimer()}),q.bind("click.multimediaview",function(a){a.preventDefault(),c.fullScreen(!c.options.fullScreen),c._resize(),c._endTimer(),a.stopPropagation()}),r.bind("vmousedown.multimediaview",function(a){var b=a.clientX,d=f.duration,e=s.offset(),g=s.width(),h=(b-e.left)/g,i=d*h;if(!f.played.length)return;f.currentTime=i,c._endTimer(),a.preventDefault(),u.bind("vmousemove.multimediaview",function(a){var b=a.clientX,c=(b-e.left)/g;f.currentTime=d*c,a.preventDefault()}).bind("vmouseup.multimediaview",function(){u.unbind("vmousemove.multimediaview vmouseup.multimediaview"),f.paused?f.pause():f.play()})}),l.bind("click.multimediaview",function(){if(c.isVolumeHide){var a=c.element,b=f.volume;c.isVolumeHide=!1,m.fadeIn("fast",function(){c._updateVolumeState(),c._updateSeekBar()}),c._resize()}else c.isVolumeHide=!0,m.fadeOut("fast",function(){c._resize()})}),n.bind("vmousedown.multimediaview",function(a){var b=a.clientX,d=o.offset().left,e=o.width(),f=d+e,g=p.offset(),h=(b-d)/e,i=(b-d)/e;c._endTimer(),c._setVolume(i.toFixed(2)),a.preventDefault(),u.bind("vmousemove.multimediaview",function(a){var b=a.clientX,f=(b-d)/e;c._setVolume(f.toFixed(2)),a.preventDefault()}).bind("vmouseup.multimediaview",function(){u.unbind("vmousemove.multimediaview vmouseup.multimediaview")})})},_removeEvent:function(){var a=this.element,b=a.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),c=b.find(".ui-playpausebutton"),d=b.find(".ui-fullscreenbutton"),e=b.find(".ui-seekbar"),f=b.find(".ui-volumecontrol"),g=f.find(".ui-volumebar"),h=f.find(".ui-handle");a.unbind(".multimediaview"),c.unbind(".multimediaview"),d.unbind(".multimediaview"),e.unbind(".multimediaview"),g.unbind(".multimediaview"),h.unbind(".multimediaview")},_createControl:function(){var b=this.element,c=b[0],d=a("<span></span>").addClass("ui-multimediaview-control"),e=a("<span></span>").addClass("ui-playpausebutton ui-button ui-play-icon"),f=a("<span></span>").addClass("ui-seekbar ui-multimediaview-bar"),g=a("<span><p>00:00:00</p></span>").addClass("ui-timestamplabel"),h=a("<span><p>00:00:00</p></span>").addClass("ui-durationlabel"),i=a("<span></span>").addClass("ui-volumebutton ui-button"),j=a("<span></span>").addClass("ui-volumecontrol"),k=a("<div></div>").addClass("ui-volumebar ui-multimediaview-bar"),l=a("<span></span>").addClass("ui-guide ui-multimediaview-bar-bg"),m=a("<span></span>").addClass("ui-value ui-multimediaview-bar-highlight"),n=a("<span></span>").addClass("ui-handle"),o=a("<span></span>").addClass("ui-fullscreenbutton ui-button"),p=a("<span></span>").addClass("ui-duration ui-multimediaview-bar-bg"),q=a("<span></span>").addClass("ui-currenttime ui-multimediaview-bar-highlight");return f.append(p).append(q).append(h).append(g),i.addClass(c.muted?"ui-mute-icon":"ui-volume-icon"),k.append(l).append(m).append(n),j.append(k),d.append(e).append(f).append(j).append(i),this._isVideo&&(a(o).addClass("ui-fullscreen-on"),d.append(o)),j.hide(),d},_startTimer:function(a){this._endTimer(),a||(a=3e3);var b=this,c=b.element,d=c.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),e=d.find(".ui-volumecontrol");b.controlTimer=setTimeout(function(){b.isVolumeHide=!0,b.controlTimer=null,e.hide(),d.fadeOut("fast")},a)},_endTimer:function(){this.controlTimer&&(clearTimeout(this.controlTimer),this.controlTimer=null)},_convertTimeFormat:function(b){if(!a.isNumeric(b))return"Playback Error";var c=parseInt(b%60,10).toString(),d=parseInt(b/60%60,10).toString(),e=parseInt(b/3600,10).toString(),f=(e.length<2?"0"+e:e)+":"+(d.length<2?"0"+d:d)+":"+(c.length<2?"0"+c:c);return f},_updateSeekBar:function(a){var b=this.element,c=b[0],d=c.duration,e=b.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),f=e.find(".ui-seekbar"),g=f.find(".ui-duration"),h=f.find(".ui-currenttime"),i=e.find(".ui-timestamplabel"),j=g.offset(),k=g.width(),l=g.height(),m=0;typeof a=="undefined"&&(a=c.currentTime),m=parseInt(a/d*k,10),g.offset(j),h.offset(j).width(m),i.find("p").text(this._convertTimeFormat(a))},_updateVolumeState:function(){var a=this.element,b=a.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),c=b.find(".ui-volumecontrol"),d=b.find(".ui-volumebutton"),e=c.find(".ui-volumebar"),f=c.find(".ui-guide"),g=c.find(".ui-value"),h=c.find(".ui-handle"),i=h.width(),j=h.height(),k=f.height(),l=f.width(),m=0,n=0,o=0,p=null,q=a[0].volume;m=parseInt(f.offset().top,10),n=parseInt(f.offset().left,10),o=n,p=h.offset(),p.top=m-parseInt((j-k)/2,10),p.left=o+parseInt(l*q,10)-parseInt(i/2,10),h.offset(p),g.offset(f.offset()).width(parseInt(l*q,10))},_setVolume:function(a){var b=this.element[0];if(a<0||a>1)return;b.volume=a},width:function(a){if(this.options.fullScreen)return;var b=this.element,c=b.parent(".ui-multimediaview-wrap");if(arguments.length===0)return b.width();this._isVideo||c.width(a),b.width(a),this._resize()},height:function(a){if(!this._isVideo||this.options.fullScreen)return;var b=this.element;if(arguments.length===0)return b.height();b.height(a),this._resize()},fullScreen:function(a){if(!this._isVideo)return;var b=this.element,c=this.options;if(arguments.length===0)return c.fullScreen;b.parents(".ui-scrollview-clip").scrollview("scrollTo",0,0),this.options.fullScreen=a,this._resize()},refresh:function(){this._resize()}}),a(b).bind("pagecreate create",function(b){a.tizen.multimediaview.prototype.enhanceWithin(b.target)}).bind("pagechange",function(b){a(b.target).find(".ui-multimediaview").each(function(){var b=a(this),c=b[0];c.autoplay&&c.play(),b.multimediaview("refresh")})}).bind("pagebeforechange",function(b){a(b.target).find(".ui-multimediaview").each(function(){var b=a(this),c=b[0],d=b.multimediaview("fullScreen");d&&b.multimediaview("fullScreen",!d),c.played.length!==0&&c.pause()})}),a(c).bind("resize orientationchange",function(b){a(".ui-page-active").find(".ui-multimediaview").multimediaview("refresh")})}(jQuery,document,window),function(a,b,c,d){function e(a,b){var c=a%b;return c<0&&(c=b+c),c}function f(a,b,c){var d="translate3d( "+b+","+c+", 0px)";a.css({"-ms-transform":d,"-o-transform":d,"-moz-transform":d,"-webkit-transform":d,transform:d})}function g(b){this.options=a.extend({},b),this.easing="easeOutQuad",this.reset()}function i(){return Date.now()}var h={scrolling:0,done:1};a.extend(g.prototype,{start:function(a,b,c){this.state=b!=0?h.scrolling:h.done,this.pos=a,this.speed=b,this.duration=c,this.fromPos=0,this.toPos=0,this.startTime=i()},reset:function(){this.state=h.done,this.pos=0,this.speed=0,this.duration=0},update:function(){var b=this.state,c,d,e,f;return b==h.done?this.pos:(c=this.duration,d=i()-this.startTime,d=d>c?c:d,e=this.speed*(1-a.easing[this.easing](d/c,d,0,1,c)),f=this.pos+e,this.pos=f,d>=c&&(this.state=h.done),this.pos)},done:function(){return this.state==h.done},getPosition:function(){return this.pos}}),jQuery.widget("mobile.circularview",jQuery.mobile.widget,{options:{fps:60,scrollDuration:2e3,moveThreshold:10,moveIntervalThreshold:150,startEventName:"scrollstart",updateEventName:"scrollupdate",stopEventName:"scrollstop",eventType:a.support.touch?"touch":"mouse",delayedClickSelector:"a, .ui-btn",delayedClickEnabled:!1},_makePositioned:function(a){a.css("position")=="static"&&a.css("position","relative")},_create:function(){var b=this;this._items=a(this.element).jqmData("list"),this._$clip=a(this.element).addClass("ui-scrollview-clip"),this._$clip.wrapInner('<div class="ui-scrollview-view"></div>'),this._$view=a(".ui-scrollview-view",this._$clip),this._$list=a("ul",this._$clip),this._$clip.css("overflow","hidden"),this._makePositioned(this._$clip),this._$view.css("overflow","hidden"),this._tracker=new g(this.options),this._timerInterval=1e3/this.options.fps,this._timerID=0,this._timerCB=function(){b._handleMomentumScroll()},this.refresh(),this._addBehaviors()},reflow:function(){var a=this.getScrollPosition();this.refresh(),this.scrollTo(a.x,a.y)},refresh:function(){var c;this._$clip.width(a(b).width()),this._clipWidth=this._$clip.width(),this._$list.empty(),this._$list.append(this._items[0]),this._itemWidth=a(this._items[0]).outerWidth(),a(this._items[0]).detach(),c=this._clipWidth/this._itemWidth,c=Math.ceil(c*10)/10,this._itemsPerView=parseInt(c,10);while(this._itemsPerView+1>this._items.length)a.merge(this._items,a(this._items).clone());this._rx=-this._itemWidth,this._sx=-this._itemWidth,this._setItems()},_startMScroll:function(a,b){this._stopMScroll();var c=!1,d=this.options.scrollDuration,e=this._tracker,f=this._clipWidth,g=this._viewWidth;this._$clip.trigger(this.options.startEventName),e.start(this._rx,a,d,g>f?-(g-f):0,0),c=!e.done(),c?this._timerID=setTimeout(this._timerCB,this._timerInterval):this._stopMScroll()},_stopMScroll:function(){this._timerID&&(this._$clip.trigger(this.options.stopEventName),clearTimeout(this._timerID)),this._timerID=0,this._tracker&&this._tracker.reset()},_handleMomentumScroll:function(){var a=!1,b=this._$view,c=0,d=0,e=this._tracker;e&&(e.update(),c=e.getPosition(),a=!e.done()),this._setScrollPosition(c,d),this._rx=c,this._$clip.trigger(this.options.updateEventName,[{x:c,y:d}]),a?this._timerID=setTimeout(this._timerCB,this._timerInterval):this._stopMScroll()},_setItems:function(){var a,b;for(a=-1;a<this._itemsPerView+1;a++)b=this._items[e(a,this._items.length)],this._$list.append(b);f(this._$view,this._sx+"px",0),this._$view.width(this._itemWidth*(this._itemsPerView+2)),this._viewWidth=this._$view.width()},_setScrollPosition:function(a,b){var c=this._sx,d=a-c,g=parseInt(d/this._itemWidth,10),h,i,j;if(g>0)for(h=0;h<g;h++)this._$list.children().last().detach(),i=-parseInt(c/this._itemWidth+h+3,10),j=this._items[e(i,this._items.length)],this._$list.prepend(j);else if(g<0)for(h=0;h>g;h--)this._$list.children().first().detach(),i=this._itemsPerView-parseInt(c/this._itemWidth+h,10),j=this._items[e(i,this._items.length)],this._$list.append(j);this._sx+=g*this._itemWidth,f(this._$view,a-this._sx-this._itemWidth+"px",0)},_enableTracking:function(){a(c).bind(this._dragMoveEvt,this._dragMoveCB),a(c).bind(this._dragStopEvt,this._dragStopCB)},_disableTracking:function(){a(c).unbind(this._dragMoveEvt,this._dragMoveCB),a(c).unbind(this._dragStopEvt,this._dragStopCB)},_getScrollHierarchy:function(){var b=[],c;return this._$clip.parents(".ui-scrollview-clip").each(function(){c=a(this).jqmData("circulaview"),c&&b.unshift(c)}),b},centerTo:function(b,c){var d,e;for(d=0;d<this._items.length;d++)if(a(this._items[d]).is(b)){e=-(d*this._itemWidth-this._clipWidth/2+this._itemWidth*1.5),this.scrollTo(e+this._itemWidth,0),this.scrollTo(e,0,c);return}},scrollTo:function(b,c,d){this._stopMScroll();if(!d){this._setScrollPosition(b,c),this._rx=b;return}var e=this,f=i(),g=a.easing.easeOutQuad,h=this._rx,j=0,k=b-h,l=0,m,n,o;this._rx=b,m=function(){n=i()-f,n>=d?(e._timerID=0,e._setScrollPosition(b,c),e._$clip.trigger("scrollend")):(o=g(n/d,n,0,1,d),e._setScrollPosition(h+k*o,j+l*o),e._timerID=setTimeout(m,e._timerInterval))},this._timerID=setTimeout(m,this._timerInterval)},getScrollPosition:function(){return{x:-this._rx,y:0}},_handleDragStart:function(b,c,d){a.each(this._getScrollHierarchy(),function(a,b){b._stopMScroll()}),this._stopMScroll(),this.options.delayedClickEnabled&&(this._$clickEle=a(b.target).closest(this.options.delayedClickSelector)),this._lastX=c,this._lastY=d,this._speedX=0,this._speedY=0,this._didDrag=!1,this._lastMove=0,this._enableTracking(),this._ox=c,this._nx=this._rx,(this.options.eventType=="mouse"||this.options.delayedClickEnabled)&&b.preventDefault(),b.stopPropagation()},_handleDragMove:function(a,b,c){this._lastMove=i();var d=b-this._lastX,e=c-this._lastY;return this._speedX=d,this._speedY=0,this._didDrag=!0,this._lastX=b,this._lastY=c,this._mx=b-this._ox,this._setScrollPosition(this._nx+this._mx,0),!1},_handleDragStop:function(a){var b=this._lastMove,c=i(),e=b&&c-b<=this.options.moveIntervalThreshold,f=this._tracker&&this._speedX&&e?this._speedX:0,g=0;return this._rx=this._mx?this._nx+this._mx:this._rx,f&&this._startMScroll(f,g),this._disableTracking(),!this._didDrag&&this.options.delayedClickEnabled&&this._$clickEle.length&&this._$clickEle.trigger("mousedown").trigger("mouseup").trigger("click"),this._didDrag&&(a.preventDefault(),a.stopPropagation()),this._didDrag?!1:d},_addBehaviors:function(){var a=this;this.options.eventType==="mouse"?(this._dragStartEvt="mousedown",this._dragStartCB=function(b){return a._handleDragStart(b,b.clientX,b.clientY)},this._dragMoveEvt="mousemove",this._dragMoveCB=function(b){return a._handleDragMove(b,b.clientX,b.clientY)},this._dragStopEvt="mouseup",this._dragStopCB=function(b){return a._handleDragStop(b)},this._$view.bind("vclick",function(b){return!a._didDrag})):(this._dragStartEvt="touchstart",this._dragStartCB=function(b){var c=b.originalEvent.targetTouches[0];return a._handleDragStart(b,c.pageX,c.pageY)},this._dragMoveEvt="touchmove",this._dragMoveCB=function(b){var c=b.originalEvent.targetTouches[0];return a._handleDragMove(b,c.pageX,c.pageY)},this._dragStopEvt="touchend",this._dragStopCB=function(b){return a._handleDragStop(b)}),this._$view.bind(this._dragStartEvt,this._dragStartCB)}}),a(c).bind("pagecreate create",function(b){a(a.mobile.circularview.prototype.options.initSelector,b.target).circularview()})}(jQuery,window,document),function(a,b){a(document).bind("pagecreate create",function(b){a(":jqmData(role='label')",b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").each(function(){a(this).addClass("jquery-mobile-ui-label").html(a("<span>",{"class":"jquery-mobile-ui-label-text"}).text(a(this).text()))})})}(jQuery),function(a,b){a.widget("tizen.fastscroll",a.mobile.widget,{options:{initSelector:":jqmData(fastscroll)"},_primaryLanguage:null,_secondLanguage:null,_dividerMap:{},_defaultTime:500,_defaultDuration:500,_timer:null,_isFadeOut:!1,_create:function(){var b=this.element,c=this,d,e=b.closest(':jqmData(role="page")'),f;this.scrollview=b.closest(".ui-scrollview-clip"),this.shortcutsContainer=a('<div class="ui-fastscroll" aria-label="Fast scroll bar, double tap to fast scroll mode" tabindex="0"/>'),this.shortcutsList=a('<ul aria-hidden="true"></ul>'),this.scrollview.append(a('<div class="ui-fastscroll-popup"></div>')),d=this.scrollview.find(".ui-fastscroll-popup"),this.shortcutsContainer.append(this.shortcutsList),this.scrollview.append(this.shortcutsContainer),this.lastListItem=b.children().last(),this.scrollview.find(".ui-scrollbar").hide(),this.jumpToDivider=function(b){var d=a(b).position().top,e=c.lastListItem.outerHeight(!0)+c.lastListItem.position().top,f=c.scrollview.height(),g=e-f,h;d=d>g?g:d,d=Math.max(d,0),c.scrollview.scrollview("scrollTo",0,-d),h=c.scrollview.offset()},this.shortcutsList.bind("touchstart mousedown vmousedown touchmove vmousemove vmouseover",function(b){var d=a.mobile.tizen.targetRelativeCoordsFromEvent(b),e=c.shortcutsList.offset();if(c._isFadeOut===!0)return;b.target.tagName.toLowerCase()==="li"&&(d.x+=a(b.target).offset().left-e.left,d.y+=a(b.target).offset().top-e.top),b.target.tagName.toLowerCase()==="span"&&(d.x+=a(b.target).parent().offset().left-e.left,d.y+=a(b.target).parent().offset().top-e.top),c.shortcutsList.find("li").each(function(){var b=a(this);a(b).removeClass("ui-fastscroll-hover").removeClass("ui-fastscroll-hover-up").removeClass("ui-fastscroll-hover-down")}),c.shortcutsList.find("li").each(function(){var b=a(this),f=b.offset().left-e.left,g=b.offset().top-e.top,h=f+Math.abs(b.outerWidth(!0)),i=g+Math.abs(b.outerHeight(!0)),j,k,l,m,n;if(d.x>=f&&d.x<=h&&d.y>=g&&d.y<=i){if(b.text()!==".")c._hitItem(b);else{m=b.data("omitSet"),j=(i-g)/m.length;for(n=0;n<m.length;n++)k=g+n*j,l=k+j,d.y>=k&&d.y<=l&&c._hitOmitItem(b,m.charAt(n))}return!1}return!0}),c._setTimer(!1),b.preventDefault(),b.stopPropagation()}).bind("touchend mouseup vmouseup vmouseout",function(){d.hide(),a(".ui-fastscroll-hover").removeClass("ui-fastscroll-hover"),a(".ui-fastscroll-hover-first-item").removeClass("ui-fastscroll-hover-first-item"),a(".ui-fastscroll-hover-up").removeClass("ui-fastscroll-hover-up"),a(".ui-fastscroll-hover-down").removeClass("ui-fastscroll-hover-down"),c._setTimer(!0)}),e&&!e.is(":visible")?e.bind("pageshow",function(){c.refresh()}):c.refresh(),b.bind("updatelayout",function(){c.refresh()}),a(window).unbind(".fastscroll").bind("resize.fastscroll",function(a){c.refresh()}),c.scrollview.bind("scrollstart",function(a){c._setTimer(!1)}).bind("scrollstop",function(a){c._setTimer(!0)})},_hitOmitItem:function(b,c){var d=this,e=d.scrollview.find(".ui-fastscroll-popup"),f=d._dividerMap[c];typeof f!="undefined"&&d.jumpToDivider(a(f)),e.text(c).css({marginLeft:-(e.width()/2),marginTop:-(e.height()/2),padding:e.css("paddingTop")}).width(e.height()).show(),a(b).addClass("ui-fastscroll-hover"),b.index()===0&&a(b).addClass("ui-fastscroll-hover-first-item"),b.index()>0&&a(b).siblings().eq(b.index()-1).addClass("ui-fastscroll-hover-up"),a(b).siblings().eq(b.index()).addClass("ui-fastscroll-hover-down")},_hitItem:function(b){var c=this,d=c.scrollview.find(".ui-fastscroll-popup"),e=b.text(),f;e==="#"?f=c._dividerMap.number:f=c._dividerMap[e],typeof f!="undefined"&&c.jumpToDivider(a(f)),d.text(e).css({marginLeft:-(d.width()/2),marginTop:-(d.height()/2),padding:d.css("paddingTop")}).width(d.height()).show(),a(b).addClass("ui-fastscroll-hover"),b.index()===0&&a(b).addClass("ui-fastscroll-hover-first-item"),b.index()>0&&a(b).siblings().eq(b.index()-1).addClass("ui-fastscroll-hover-up"),a(b).siblings().eq(b.index()).addClass("ui-fastscroll-hover-down")},_focusItem:function(b){var c=this,d=c.scrollview.find(".ui-fastscroll-popup");b.focusin(function(a){c.shortcutsList.attr("aria-hidden",!1),c._hitItem(b),c._setTimer(!1)}).focusout(function(b){c.shortcutsList.attr("aria-hidden",!0),d.hide(),a(".ui-fastscroll-hover").removeClass("ui-fastscroll-hover"),a(".ui-fastscroll-hover-first-item").removeClass("ui-fastscroll-hover-first-item"),a(".ui-fastscroll-hover-up").removeClass("ui-fastscroll-hover-up"),a(".ui-fastscroll-hover-down").removeClass("ui-fastscroll-hover-down"),c._setTimer(!0)})},_contentHeight:function(){var b=this,c=a(".ui-scrollview-clip"),d=null,e=null,f=0,g=a(window).height();return c.hasClass("ui-content")?(f=parseInt(c.css("padding-top"),10),g-=f||0,f=parseInt(c.css("padding-bottom"),10),g-=f||0,d=c.siblings(".ui-header:visible"),e=c.siblings(".ui-footer:visible"),d&&(d.outerHeight(!0)===null?g-=a(".ui-header").outerHeight()||0:g-=d.outerHeight(!0)),e&&(g-=e.outerHeight(!0))):g=c.height(),g},_omit:function(a,b){var c=parseInt((b-1)/2,10),d=a-b,e=[],f=[],g,h,i,j;if(b<3||a<=b)return;d>=c?(i=2,h=1,g=c):(i=b/(d+1),h=i,g=d);for(j=0;j<g;j++)e.push(parseInt(h,10)),h+=i;for(j=0;j<b;j++)f.push(1);for(j=0;j<d;j++)f[e[j%c]]++;return f},_createDividerMap:function(){var b=this,c=b._primaryLanguage?b._primaryLanguage.replace(/,/g,""):null,d=b._secondLanguage?b._secondLanguage.replace(/,/g,""):null,e="0123456789",f=b.element.find(".ui-li-divider"),g={},h,i,j,k;h=function(b,c){a(c).text()===j&&(g[j]=c)},i=function(b,d){c+=a(d).text()},c===null&&(c="",f.each(i));for(k=0;k<c.length;k++)j=c.charAt(k),f.each(h);if(d!==null)for(k=0;k<d.length;k++)j=d.charAt(k),f.each(h);f.each(function(b,c){if(e.search(a(c).text())!==-1)return g.number=c,!1}),b._dividerMap=g},_setTimer:function(a){var b=this;a===!0?b._timer=setTimeout(function(){b._isFadeOut=!0,b.shortcutsContainer.fadeOut(b._defaultDuration,function(){b._isFadeOut=!1})},b._defaultTime):(b._timer!==null&&clearTimeout(b._timer),b.shortcutsContainer.show())},indexString:function(a){var b=this,c=[];if(typeof a=="undefined")return b._primaryLanguage+":"+b._secondLanguage;c=a.split(":"),b._primaryLanguage=c[0],c.length===2&&(b._secondLanguage=c[1])},refresh:function(){var b=this,c=b._primaryLanguage?b._primaryLanguage.replace(/,/g,""):null,d=b._secondLanguage?b._secondLanguage.replace(/,/g,""):null,e=b._contentHeight(),f=a('<li tabindex="0" aria-label="double to move Number list"><span aria-hidden="true">#</span><span aria-label="Number"/></li>'),g=0,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,A,B,C,D;h=function(b,d){c+=a(d).text()},i=function(a,b){var d,e="";for(d=0;d<b;d++)e+=c[a+d];return e},j=function(c){var d=a(this).text(),e=b._dividerMap[d];typeof e!="undefined"&&a(e).next().focus()},b._createDividerMap(),b.shortcutsList.find("li").remove(),u=b.element.find(".ui-li-divider"),v=b.element.find("li").not(".ui-li-divider"),u=u.filter(":visible"),v=v.filter(":visible");if(u.length<2){b.shortcutsList.hide();return}b.shortcutsList.show(),b.lastListItem=v.last(),b.shortcutsList.append(f),b._focusItem(f),c===null&&(c="",u.each(h)),s=parseInt(f.css("padding"),10),r=f.height()+s*2,p=parseInt(e/r-1,10),q=c.length,p=d?p-2:p;if(p<3){f.remove();return}t=b._omit(q,p);for(D=0;D<c.length;D++)y=c.charAt(D),m=a('<li tabindex="0" aria-label="double to move '+y+' list">'+y+"</li>"),b._focusItem(m),typeof t!="undefined"&&t[g]>1?(m=a("<li>.</li>"),m.data("omitSet",i(D,t[g])),D+=t[g]-1):m.bind("vclick",j),f.before(m),g++;if(d!==null){z=d.length-1,A=[],A.push(d.charAt(0)),A.push(d.charAt(z));for(D=0;D<A.length;D++)y=A[D],m=a('<li tabindex="0" aria-label="double to move '+y+' list">'+y+"</li>"),b._focusItem(m),m.bind("vclick",j),f.before(m)}k=b.shortcutsContainer.outerHeight(),w=e-k,l=b.shortcutsList.children(),C=parseInt(w/l.length,10),x=w-l.length*C,w>0&&l.each(function(b,c){B=a(c).height()+C,x!==0&&(B+=1,x-=1),a(c).css({height:B,lineHeight:B+"px"})}),n=u.first().position().top,b.shortcutsContainer.css("top",n),o=n+b.shortcutsContainer.outerHeight()+"px",b.scrollview.css("min-height",o),b._setTimer(!1),b._setTimer(!0)}}),a(document).bind("pagecreate create",function(b){a(a.tizen.fastscroll.prototype.options.initSelector,b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").fastscroll()})}(jQuery);var ensureNS=function(){var a={};return function(c){var d=c.split(".").reverse(),e="",f="",g="",h=d.length;while(--h>=0)g=d[h],e=e+(e.length>0?".":"")+g,a[e]||(a[e]=!0,f+="!window."+e+" && (window."+e+" = {});\n");f.length&&(new Function(f))()}}();(function(a,b){a.webgl={},a.webgl.shader={_vertexShader:null,_fragmentShader:null,deleteShaders:function(a){a.deleteShader(this._vertexShader),a.deleteShader(this._fragmentShader)},addShaderProgram:function(a,b,c,d){var e,f={},g={};return d?(f=this.loadShaderFile(b),g=this.loadShaderFile(c)):(f.source=b,g.source=c),this._vertexShader=this.getShader(a,a.VERTEX_SHADER,f),this._fragmentShader=this.getShader(a,a.FRAGMENT_SHADER,g),e=a.createProgram(),a.attachShader(e,this._vertexShader),a.attachShader(e,this._fragmentShader),a.linkProgram(e),a.getProgramParameter(e,a.LINK_STATUS)||window.alert("Could not initialize Shaders!"),e},loadShaderFile:function(b){var c=null;return a.ajax({async:!1,url:b,success:function(a){c={source:a}}}),c},getShader:function(a,b,c){var d;return!a||!b||!c?null:(d=a.createShader(b),a.shaderSource(d,c.source),a.compileShader(d),a.getShaderParameter(d,a.COMPILE_STATUS)?d:(window.alert(a.getShaderInfoLog(d)),a.deleteShader(d),null))}},a.webgl.buffer={attribBufferData:function(a,b){var c=a.createBuffer();return a.bindBuffer(a.ARRAY_BUFFER,c),a.bufferData(a.ARRAY_BUFFER,b,a.STATIC_DRAW),a.bindBuffer(a.ARRAY_BUFFER,null),c}}})(jQuery),function(a,b,c){pinch_event={setup:function(){function f(a){var b=a[0].x-a[1].x,c=a[0].y-a[1].y;return Math.abs(b*c)}function g(a,b){return{point:a,ratio:b}}var d=this,e=a(d);if(!a.mobile.support.touch)return;e.bind("touchstart",function(d){function l(c){var d=c.originalEvent.touches,e,h,l,m=a(b).width()/a.mobile.pinch.factor;if(k)return;if(!i)return;e=[{x:d[0].pageX,y:d[0].pageY},{x:d[1].pageX,y:d[1].pageY}],l=Math.sqrt(f(e)/f(i)),l&&(h=l),h<a.mobile.pinch.min?h=a.mobile.pinch.min:h>a.mobile.pinch.max&&(h=a.mobile.pinch.max);if(Math.abs(h-j)<a.mobile.pinch.threshold)return;a(c.target).trigger("pinch",g(e,h)),j=h,a.mobile.pinch.interval&&(k=!0,setTimeout(function(){k=!1},a.mobile.pinch.interval))}var h=d.originalEvent.touches,i,j=1,k=!1;if(!a.mobile.pinch.enabled)return;if(h.length!=2)return;i=[{x:h[0].pageX,y:h[0].pageY},{x:h[1].pageX,y:h[1].pageY}],a(d.target).trigger("pinchstart",g(i,c)),e.bind("touchmove",l).one("touchend",function(b){e.unbind("touchmove",l),a(b.target).trigger("pinchend",g(c,j)),i=c,current=c,j=1,k=!1})})}},a.event.special.pinch=pinch_event,a.mobile.pinch={enabled:!0,min:.1,max:3,factor:4,threshold:.01,interval:50}}(jQuery,this),function(a,b,c,d){function g(){if(f)return;e=c.createElement("canvas"),f=e.getContext("2d")}function h(a){var c=b.FileError,d="";switch(a.code){case c.QUOTA_EXCEEDED_ERR:d="QUOTA_EXCEEDED_ERR";break;case c.NOT_FOUND_ERR:d="NOT_FOUND_ERR";break;case c.SECURITY_ERR:d="SECURITY_ERR";break;case c.INVALID_MODIFICATION_ERR:d="INVALID_MODIFICATION_ERR";break;case c.INVALID_STATE_ERR:d="INVALID_STATE_ERR";break;default:d="Unknown Error"}return d}function i(a){var b=a.replace(/\//gi,"_");return b}function j(a,b,c,d,e){var f=0,g=0,h=0,i=0,j=a/c,k=b/d,l=Math.max(j,k);return e?(f=c,g=d):(l>1?(f=a/l,g=b/l):(f=a,g=b),h=(c-f)/2,i=(d-g)/2),{w:f,h:g,x:h,y:i}}function k(a,b,c,d){var h,i;return g(),e.width=b,e.height=c,h=j(a.width,a.height,b,c,d),f.fillStyle="#000000",f.fillRect(0,0,b,c),f.drawImage(a,h.x,h.y,h.w,h.h),i=e.toDataURL(),i}var e,f;a.imageloader={_grantedBytes:1048576,getThumbnail:function(a,b){function e(a){var c=h(a);b&&b(c==="NOT_FOUND_ERR"?c:null)}var c,d;c=i(a);try{d=localStorage.getItem(c),b&&b(d===null?"NOT_FOUND_ERR":d)}catch(f){b&&b(f.type==="non_object_property_load"?"NOT_FOUND_ERR":null)}},setThumbnail:function(a,b,c,d,e){function l(a){var c=h(a);b&&b(c==="NOT_FOUND_ERR"?c:null)}var f,g,j;c=c||128,d=d||128,e=e||!0,f=new Image,f.onload=function(){g=i(a),j=k(this,c,d,e);try{localStorage.setItem(g,j),b&&b(j)}catch(f){b&&b(f.type==="non_object_property_load"?"NOT_FOUND_ERR":null)}},f.src=a},removeThumbnail:function(a){function c(a){h(a)}var b;b=i(a);try{localStorage.removeItem(b)}catch(d){throw d}}}}(jQuery,window,document),function(a,b,c,d){a.widget("tizen.splitview",a.mobile.widget,{options:{fixed:!1,dividerVertical:!0,ratio:[],initSelector:":jqmData(role='splitview')"},_create:function(){var c=this,d=c.element,e=c.options,f=d.children(".ui-pane"),g=f.length,h=[],i=[],j=this.element.attr("data-ratio"),k=[0,0],l=null,m=0;if(g!==2){if(g<2)for(m=g;m<2;++m)c._addEmptyPanes();else f.slice(2).remove();f=d.children(".ui-pane"),g=f.length}h[0]=a("<a href='#' class='ui-spliter' aria-label='Drag scroll, double tap and move to adjust split area'></a>").insertAfter(f[0]),i[0]=a("<div class='ui-spliter-bar'></div>").appendTo(h[0]),a("<div class='ui-spliter-handle'></div>").appendTo(i[0]),a.extend(this,{moveTarget:null,moveData:{},spliters:h,spliterBars:i,panes:f,containerSize:k,touchStatus:!1,minPaneWidth:50,savedRatio:[]}),c._bindTouchEvents(),c._convertRatio(j,f.length),d.addClass("ui-splitview ui-direction-"+c._direction(e.dividerVertical)),c._refresh(),a(b).unbind(".splitview").bind("pagechange.splitview resize.splitview",function(b){a(".ui-page-active .ui-splitview").each(function(){a(this).data("splitview")._refresh()})})},_addEmptyPanes:function(){var b=this,c=b.element,d=b.options,e=c.children(".ui-pane"),f=a.support.scrollview?"data-scroll='y'":"",g=a("<div class='ui-pane' "+f+"></div>");f.length&&g.scrollview({direction:"y"}),e.length?e.last().after(g):c.append(g)},_direction:function(a){return a?"horizontal":"vertical"},_isStyleSpecified:function(a){return typeof a!="undefined"&&a.length},_getContainerSize:function(a,b){var c=this,d=c.element,e=c._isStyleSpecified(a),f=c._isStyleSpecified(b);return c.containerSize[0]=e?d.outerWidth(!0):c._parentWidth(),c.containerSize[1]=f?d.outerHeight(!0):c._parentHeight(),!c.containerSize[0]||!c.containerSize[1]?!1:!0},_parentWidth:function(){var c=this.element.parent();return!c&&typeof c=="undefined"&&!c.length?a(b).width():c.width()},_parentHeight:function(){var c=this.element.parent(),d="",e=!1,f=0;while(c&&typeof c!="undefined"&&c.length){if(typeof c[0].style!="undefined"){d=c[0].style.height,e=typeof d!="undefined"&&d.length;if(e){f=c.height();break}}c=c.parent()}return e||(f=a(b).height()),f},_convertRatio:function(b,c){var d=this,e=[],f=0,g=typeof b,h=null,i;for(i=0;i<c;++i)e.push(0);switch(g){case"number":c&&(e[0]=b);break;case"string":h=b.split(","),f=Math.min(h.length,c);for(i=0;i<f;++i)e[i]=parseFloat(h[i]);break;case"object":if(!a.isArray(b))break;f=Math.min(b.length,c);for(i=0;i<f;++i)g=typeof b[i],e[i]=g==="string"?parseFloat(b[i]):g==="number"?b[i]:0}d.options.ratio=e,d._adjustRatio(c)},_adjustRatio:function(a){var b=this,c=b.options.ratio,d=0,e=0,f=0,g=0,h=0,i;if(!a){b.options.ratio=[];return}for(i in c)d+=c[i];if(d!==1){e=1-d,f=e/a;for(i in c)f>=0?(c[i]+=f,e=Math.max(0,e-f)):(h+=f,g=Math.max(h,c[i]*-1),c[i]=Math.max(0,c[i]+g),e=Math.min(0,e-g),h-=g);if(e)if(e>0)c[c.length-1]+=e;else for(i=c.length-1;i>=0;--i){g=Math.max(e,c[i]*-1),c[i]=Math.max(0,c[i]+g),e=Math.min(0,e-g);if(!e)break}b.options.ratio=c}},_setOption:function(b,c){var d=this,e=d.options[b];if(e===c)return;a.Widget.prototype._setOption.apply(this,arguments);switch(b){case"fixed":d._fixed(c);break;case"dividerVertical":d._dividerVertical(c);break;case"ratio":d._ratio(c)}},_subtractDiffWidth:function(a,b){var c=this;return a<=c.minPaneWidth?{width:a,diff:b}:(a+=b,a>=c.minPaneWidth?{width:a,diff:0}:{width:c.minPaneWidth,diff:a-c.minPaneWidth})},_initRatio:function(b,c,d,e){var f=this,g=0,h=[],i=0,j=c.length,k,l;c.each(function(b){var c=a(this);h.push(d?c.width():c.height()),g+=h[b]}),i=e-g;if(!i)return h;if(i>0)h[b?0:j-1]+=i;else if(b)for(l=0;l<j;++l){k=f._subtractDiffWidth(h[l],i),h[l]=k.width,i=k.diff;if(!i)break}else for(l=j-1;l>=0;--l){i=f._subtractDiffWidth(h[l],i),h[l]=k.width,i=k.diff;if(!i)break}g=0;for(l in h)g+=h[l];for(l in f.options.ratio)f.options.ratio[l]=h[l]/g;return h},_horizontalBoundary:function(){var a=this,b=a.element;return b.outerWidth(!0)-b.width()},_verticalBoundary:function(){var a=this,b=a.element;return b.outerHeight(!0)-b.height()},_boundary:function(a){var c=this,d=c.element,e=b.getComputedStyle(d[0],null),f=parseFloat(e["margin"+a]),g=parseFloat(e["border"+a+"Width"]),h=parseFloat(e["padding"+a]);return{margin:f,border:g,padding:h}},_layout:function(b,c){var d=this,e=d.element,f=d.options,g=f.dividerVertical,h=d.panes,i=d.spliters,j=d.spliterBars,k=d.spliterBars.length?a(j[0]):null,l=k?g?k.outerWidth():k.outerHeight():0,m=k?g?k.outerWidth(!0)-k.outerWidth():k.outerHeight(!0)-k.outerHeight():0,n=h.length,o=0,p=l*(n-1),q=d.containerSize[0],r=d.containerSize[1],s=q-d._horizontalBoundary(),t=r-d._verticalBoundary(),u=g?t:s,v=g?s-p:t-p,w=[],x=0,y=null;b=!!b,c=!!c,e.css({"min-width":s,"min-height":t}),b&&(w=d._initRatio(c,h,g,v)),o=v,h.each(function(c){var e=a(this),f=b?w[c]:Math.floor(v*d.options.ratio[c]),i=c?h.eq(c-1):null,j=0,k=0,m=0,p=0;o-=f,c===n-1&&(f=Math.max(Math.min(f,d.minPaneWidth),f+o)),x+=f,i?(j=parseInt(i.css(g?"left":"top"
-),10),j+=g?i.width():i.height(),j+=l):(p=d._boundary(g?"Left":"Top"),j=p.padding),k=g?f:u,m=g?u:f,e.css({width:k,height:m}),e.css(g?"left":"top",j)}),h.each(function(b){var c=a(this),e=g?c.width():c.height();d.options.ratio[b]=e/x}),a.each(i,function(b){var c=a(this),d=h.eq(b),e=c.children(".ui-spliter-bar"),f=e.children(".ui-spliter-handle"),i=0;g?(i=parseInt(d.css("left"),10)+d.width()-m,c.outerHeight(u).css("left",i)):(i=parseInt(d.css("top"),10)+d.height()-m,c.outerWidth(u).css("top",i)),e.length&&e[g?"outerHeight":"outerWidth"](u),f.length&&f.css(g?"top":"left",(u-l)/2)}),y=e.find(".ui-splitview:first");if(!y.length)return;y=y.data("splitview"),y&&y._refresh()},_bindTouchEvents:function(){var b=this,c=b.element,d=b.panes,e=b.spliters;a.each(e,function(c){var d=a(this);b._bindSpliterTouchEvents.call(b,d)})},_bindSpliterTouchEvents:function(b){var d=this,e=d.element,f=d.options,g=a.support.touch?"touchstart":"mousedown",h=(a.support.touch?"touchmove":"mousemove")+".splitview",i=(a.support.touch?"touchend":"mouseup")+".splitview";b.bind(g,{e:b},function(b){if(d.options.fixed)return;var g=a.support.touch?b.originalEvent.changedTouches[0]:b,j=b.data.e,k=j.prev(),l=j.next(),m=k.find(".ui-splitview:first"),n=l.find(".ui-splitview:first"),o=f.dividerVertical,p=o?a(d.spliterBars[0]).outerWidth():a(d.spliterBars[0]).outerHeight();d.moveTarget=j,d.moveData={spliterWidth:p||0,prevPane:k,nextPane:l,splitviewInPrev:m,splitviewInNext:n,prevPanePos:parseInt(k.css(o?"left":"top"),10)||0,prevPaneWidth:parseInt(k.css(o?"width":"height"),10)||0,nextPanePos:parseInt(l.css(o?"left":"top"),10)||0,nextPaneWidth:parseInt(l.css(o?"width":"height"),10)||0,targetPos:parseInt(j.css(o?"left":"top"),10)||0,pagePos:o?g.pageX:g.pageY},j.addClass("ui-spliter-active"),e.bind(h,function(b){if(!d.touchStatus)return;b.stopPropagation(),d._drag(a.support.touch?b.originalEvent.changedTouches[0]:b)}).bind(i,function(b){b.stopPropagation(),d._stop(a.support.touch?b.originalEvent.changedTouches[0]:b),d.touchStatus=!1,e.unbind(".splitview"),a(c).unbind(".splitview")}),a(c).bind(h+" "+i,function(){e.trigger(i)}),b.preventDefault(),d.touchStatus=!0})},_drag:function(a){if(!this.moveData||typeof this.moveData=="undefined")return;var b=this,c=b.element,d=b.options,e=d.dividerVertical,f=b.moveData,g=b.moveTarget,h=f.prevPane,i=f.nextPane,j=f.splitviewInPrev,k=f.splitviewInNext,l=f.spliterWidth,m=null,n=null,o=null,p=null,q=null,r=e?a.pageX:a.pageY,s=null;m=r-f.pagePos,m>0?m=Math.min(Math.max(f.nextPaneWidth-b.minPaneWidth,0),m):m=Math.max(Math.max(f.prevPaneWidth-b.minPaneWidth,0)*-1,m),o=f.nextPanePos+m,p=Math.max(f.prevPaneWidth+m,0),q=Math.max(f.nextPaneWidth-m,0),n=f.targetPos+m,g.css(e?{left:n}:{top:n}),h.css(e?{width:p}:{height:p}),i.css(e?{width:q,left:o}:{height:q,top:o}),j.length&&(s=j.data("splitview"),s._refresh(!0,!1)),k.length&&(s=k.data("splitview"),s._refresh(!0,!0))},_stop:function(b){if(!this.moveData||!this.moveTarget)return;var c=this,d=c.element,e=c.options,f=c.panes,g=f.length,h=e.dividerVertical,i=c.moveData,j=c.moveTarget,k=i.prevPane,l=i.nextPane,m=i.splitviewInPrev,n=i.splitviewInNext,o=i.spliterWidth,p=o*(g-1),q=null,r=null,s=null,t=null,u=null,v=d.css("display"),w=c.containerSize[0],x=c.containerSize[1],y=w-c._horizontalBoundary(),z=x-c._verticalBoundary(),A=h?y-p:z-p,B=0;j.removeClass("ui-spliter-active"),f.each(function(b){var c=a(this),d=h?c.width():c.height();B+=d}),f.each(function(b){var d=a(this),e=h?d.width():d.height();c.options.ratio[b]=e/B}),c.moveData=null},_fixed:function(b){var c=this,d=c.spliters;a.each(d,function(c){var d=a(this);b?d.addClass("ui-fixed"):d.removeClass("ui-fixed")}),c._layout()},_dividerVertical:function(a){var b=this,c=b.element,d=a,e=null,f=null,g=null,h=null;e=c.children(".ui-pane"),f=c.children(".ui-spliter"),g=f.children(".ui-spliter-bar"),h=g.children(".ui-spliter-handle"),c.removeClass("ui-direction-vertical"),c.removeClass("ui-direction-horizontal"),c.addClass("ui-splitview ui-direction-"+b._direction(d)),e.css({left:"",top:"",width:"",height:""}),f.css({left:"",top:"",width:"",height:""}),g.css({width:"",height:""}),h.css({left:"",top:""}),b._getContainerSize(c[0].style.width,c[0].style.height)&&b._layout()},_ratio:function(a){var b=this,c=b.element,d=c.children(".ui-pane"),e=d.length;b._convertRatio(a,e),b._layout()},_refresh:function(a,b){var c=this,d=c.element;a=!!a,b=!!b,c._getContainerSize(d[0].style.width,d[0].style.height)&&c._layout(a,b)},pane:function(a,b){if(typeof a!="string")return null;var c=this,d=c.element,e=d.children(a),f=null,g=null;if(!e.hasClass("ui-pane"))return null;if(!b)return e.contents();if(e.hasClass("ui-scrollview-clip")){e.scrollview("scrollTo",0,0,0),f=e.children(".ui-scrollview-view");if(!f.length)return null}else f=e;g=b.parent();if(g.length&&g[0]===f[0])return;f.empty().append(b).trigger("create"),f.fadeIn("fast")},maximize:function(a){if(typeof a!="string")return;var b=this,c=b.element,d=b.panes,e=c.children(a);if(!e.hasClass("ui-pane"))return;b.savedRatio=b.options.ratio.slice(),b.options.ratio=[],d.each(function(a){b.options.ratio.push(this===e[0]?1:0)}),b._layout()},restore:function(){var a=this;if(!a.savedRatio.length)return;a.options.ratio=a.savedRatio.slice(),a._adjustRatio(a.panes.length),a._layout()}}),a(c).bind("pagecreate create",function(b){a.tizen.splitview.prototype.enhanceWithin(b.target)})}(jQuery,window,document),function(a,b,c){var d=Math.PI/2,e=.001,f={},g=b.vec3,h=function(a,b){var c=[b[0]-a[0],b[1]-a[1],b[2]-a[2]],d=Math.sqrt(c[0]*c[0]+c[1]*c[1]+c[2]*c[2]);return d};f.base=function(){},f.base.prototype={points:[],step:e,length:0,levels:[],init:function(a){},calculateLevel:function(a){},calculateTotalLength:function(){},getPosition:function(a){},getPercent:function(a,b){},getAngle:function(a){}},f.bezier2d=function(){},f.bezier2d.prototype=a.extend(!0,{},f.base.prototype,{init:function(a){this.points=a.points,this.step=a.step||e,this.length=this.calculateTotalLength(),this.levels=this.calculateLevel(a.maxLevel)||[]},calculateLevel:function(a){var b=this.length,c=b/a,d=[],e;if(!a)return null;for(e=0;e<a;e+=1)d[a-e]=this.getPercent(0,c*e);return d},calculateTotalLength:function(){var a=this.step,b=this.getPosition(0),c=b,d=0,e;for(e=a;e<=1;e+=a)b=this.getPosition(e),d+=h(c,b),c=b;return d},getPosition:function(a){var b=this.points,c=function(a,b,c,d,e){return Math.pow(1-e,3)*a+3*e*Math.pow(1-e,2)*b+3*Math.pow(e,2)*(1-e)*c+Math.pow(e,3)*d},d=[c(b[0][0],b[1][0],b[2][0],b[3][0],a),c(b[0][2],b[1][2],b[2][2],b[3][2],a)];return[d[0],0,d[1]]},getPercent:function(a,b){var c=this.step,d=this.getPosition(a=a||0),e=d,f=a+b,g=0,i;for(i=a+c;i<=1;i+=c){d=this.getPosition(i),g+=h(e,d);if(g>=f)return i;e=d}return 1},getAngle:function(a){var b=this.points,c=function(a,b,c,d,e){return 3*e*e*(-a+3*b-3*c+d)+6*e*(a-2*b+c)+3*(-a+b)},e=c(b[0][0],b[1][0],b[2][0],b[3][0],a),f=c(b[0][2],b[1][2],b[2][2],b[3][2],a);return Math.atan2(e,f)-d}}),f.bspline=function(){},f.bspline.prototype=a.extend(!0,{},f.base.prototype,{_degree:3,_numberOfControls:0,_knotVectors:[],_numberOfKnots:0,init:function(a){this.points=a.points,this.step=a.step||e,this._numberOfPoints=this.points.length-1,this._numberOfKnots=this._numberOfPoints+this._degree+1;var b=1/(this._numberOfKnots-2*this._degree),c=b,d=0;while(d<=this._numberOfKnots)d<=this._degree?this._knotVectors.push(0):d<this._numberOfKnots-this._degree+1?(this._knotVectors.push(c),c+=b):this._knotVectors.push(1),d+=1;this.length=this.calculateTotalLength(),this.levels=this.calculateLevel(a.maxLevel)||[]},_Np:function(a,b,c){var d=this._knotVectors,e=0,f=0,g=0,h=function(a,b){return d[b]<=a&&a<d[b+1]?1:0};return c===1?(e=h(a,b),f=h(a,b+1)):(e=this._Np(a,b,c-1),f=this._Np(a,b+1,c-1)),g=d[b+c]-d[b],e*=g!==0?(a-d[b])/g:0,g=d[b+c+1]-d[b+1],f*=g!==0?(d[b+c+1]-a)/g:0,e+f},calculateLevel:function(a){var b=this.length,c=b/a,d=[],e;if(!a)return null;for(e=0;e<a;e+=1)d[a-e]=this.getPercent(0,c*e);return d},calculateTotalLength:function(){var a=this.step,b=this.getPosition(0),c=b,d=0,e;for(e=a;e<=1;e+=a)b=this.getPosition(e),d+=h(c,b),c=b;return d},getPosition:function(a){var b=[],c,d,e;a=a.toFixed(4);for(d=0;d<3;d+=1){e=0;for(c=0;c<=this._numberOfPoints;c+=1)e+=this.points[c][d]*this._Np(a,c,this._degree);b[d]=e}return b},getPercent:function(a,b){var c=this.step,d=this.getPosition(a=a||0),e=d,f=a+b,g=0,i;for(i=a+c;i<=1;i+=c){d=this.getPosition(i),g+=h(e,d);if(g>=f)return i;e=d}return 1},getAngle:function(a){var b=this.getPosition(a),c=this.getPosition(a+.001),d=g.normalize(g.direction(b,c)),e=g.dot(d,[1,0,0]);return Math.acos(e)+Math.PI}}),a.motionpath=function(a,b){var c=new f[a];return c.init(b),c}}(jQuery,window),function(a,b){var c={};a.widget("tizen.extendablelist",a.mobile.widget,{options:{theme:"s",countTheme:"c",headerTheme:"b",dividerTheme:"b",splitIcon:"arrow-r",splitTheme:"b",inset:!1,id:"",extenditems:50,childSelector:" li",dbtable:"",template:"",loadmore:"tmp_load_more",scrollview:!1,initSelector:":jqmData(role='extendablelist')"},_stylerMouseUp:function(){a(this).addClass("ui-btn-up-s"),a(this).removeClass("ui-btn-down-s")},_stylerMouseDown:function(){a(this).addClass("ui-btn-down-s"),a(this).removeClass("ui-btn-up-s")},_stylerMouseOver:function(){a(this).toggleClass("ui-btn-hover-s")},_stylerMouseOut:function(){a(this).toggleClass("ui-btn-hover-s"),a(this).addClass("ui-btn-up-s"),a(this).removeClass("ui-btn-down-s")},_pushData:function(b){var c=this.options,d=this,e=0,f=a("#"+b),g=c.extenditems>d._numItemData-d._lastIndex?d._numItemData-d.lastIndex:c.extenditems,h;for(e=0;e<g;e++)h=f.tmpl(d._itemData(e)),a(c.id).append(a(h).attr("id","li_"+e)),a(c.id+">"+c.childSelector).addClass("ui-btn-up-s").bind("mouseup",d._stylerMouseUp).bind("mousedown",d._stylerMouseDown).bind("mouseover",d._stylerMouseOver).bind("mouseout",d._stylerMouseOut),d._lastIndex+=1;a(c.id).trigger("create")},_loadmore:function(b){var c=b.data,d=c.options,e=0,f=a("#"+d.template),g=d.extenditems>c._numItemData-c._lastIndex?c._numItemData-c._lastIndex:d.extenditems,h,i,j;a("#load_more_message").remove();for(e=0;e<g;e++)h=f.tmpl(c._itemData(c._lastIndex)),a(d.id).append(a(h).attr("id","li_"+c._lastIndex)),c._lastIndex+=1;c._numItemData>c._lastIndex&&(f=a("#"+d.loadmore),i=c._numItemData-c._lastIndex,j=d.extenditems<=i?d.extenditems:i,h=f.tmpl({NUM_MORE_ITEMS:j}),a(d.id).append(a(h).attr("id","load_more_message").css("min-height","37px"))),a(d.id).trigger("create"),a(d.id).extendablelist("refresh")},recreate:function(a){this._create({itemData:function(b){return a[b]},numItemData:a.length})},_initList:function(b){var c=this,d=this.options,e,f,g,h;c._lastIndex<=0&&(c._pushData(d.template),c._numItemData>c._lastIndex?(e=a("#"+d.loadmore),f=c._numItemData-c._lastIndex,g=d.extenditems<=f?d.extenditems:f,h=e.tmpl({NUM_MORE_ITEMS:g}),a(d.id).append(a(h).attr("id","load_more_message").css("min-height","37px")),a("#load_more_message").live("click",c,c._loadmore)):(a("#load_more_message").die(),a("#load_more_message").remove())),d.childSelector==" ul"&&a(d.id+" ul").swipelist(),a(d.id).trigger("create"),c.refresh(!0)},create:function(){var a=this.options;this._create.apply(this,arguments)},_create:function(b){var c=this,d=this.options,e=this.element,f;c.destroy(),a.extend(this,{_itemData:function(a){return null},_numItemData:0,_cacheItemData:function(a,b){},_lastIndex:0}),c.element.addClass(function(a,b){return b+" ui-listview ui-extendable-list-container"+(c.options.inset?" ui-listview-inset ui-corner-all ui-shadow ":"")}),d.id="#"+e.attr("id"),e.data("extenditems")&&(d.extenditems=parseInt(e.data("extenditems"),10)),a(d.id).bind("pagehide",function(b){a(d.id).empty()}),a(".ui-scrollview-clip").size()>0?d.scrollview=!0:d.scrollview=!1;if(b){if(!c._loadData(b))return}else{console.warn("WARNING: The data interface of extendable list is changed. \nOld data interface(data-dbtable) is still supported, but will be removed in next version. \nPlease fix your code soon!");if(!a(d.id).hasClass("elLoadSuccess")){console.warn("No elLoadSuccess class");return}f=e.jqmData("dbtable"),d.dbtable=window[f],d.dbtable||(d.dbtable={}),c._itemData=function(a){return d.dbtable[a]},c._numItemData=d.dbtable.length}e.data("template")&&(d.template=e.data("template"),e.data("swipelist")==1?d.childSelector=" ul":d.shildSelector=" li"),c._initList(b)},_loadData:function(a){var b=this;if(!a.itemData||typeof a.itemData!="function")return!1;b._itemData=a.itemData;if(!a.numItemData)return!1;if(typeof a.numItemData=="function")b._numItemData=a.numItemData();else{if(typeof a.numItemData!="number")return!1;b._numItemData=a.numItemData}return!0},destroy:function(){var b=this.options,c=0,d=0;a(b.id).empty(),a("#load_more_message").die()},_itemApply:function(b,c){var d=c.find(".ui-li-count");d.length&&c.addClass("ui-li-has-count"),d.addClass("ui-btn-up-"+(b.jqmData("counttheme")||this.options.countTheme)+" ui-btn-corner-all"),c.find("h1, h2, h3, h4, h5, h6").addClass("ui-li-heading").end().find("p, dl").addClass("ui-li-desc").end().find(">img:eq(0), .ui-link-inherit>img:eq(0)").addClass("ui-li-thumb").each(function(){c.addClass(a(this).is(".ui-li-icon")?"ui-li-has-icon":"ui-li-has-thumb")}).end().find(".ui-li-aside").each(function(){var b=a(this);b.prependTo(b.parent())})},_removeCorners:function(a,b){var c="ui-corner-top ui-corner-tr ui-corner-tl",d="ui-corner-bottom ui-corner-br ui-corner-bl";a=a.add(a.find(".ui-btn-inner, .ui-li-link-alt, .ui-li-thumb")),b==="top"?a.removeClass(c):b==="bottom"?a.removeClass(d):a.removeClass(c+" "+d)},_refreshCorners:function(a){var b,c,d,e;this.options.inset&&(b=this.element.children("li"),c=a?b.not(".ui-screen-hidden"):b.filter(":visible"),this._removeCorners(b),d=c.first().addClass("ui-corner-top"),d.add(d.find(".ui-btn-inner")).find(".ui-li-link-alt").addClass("ui-corner-tr").end().find(".ui-li-thumb").not(".ui-li-icon").addClass("ui-corner-tl"),e=c.last().addClass("ui-corner-bottom"),e.add(e.find(".ui-btn-inner")).find(".ui-li-link-alt").addClass("ui-corner-br").end().find(".ui-li-thumb").not(".ui-li-icon").addClass("ui-corner-bl"))},refresh:function(b){this.parentPage=this.element.closest(".ui-page"),this._createSubPages();var c=this.options,d=this.element,e=this,f=d.jqmData("dividertheme")||c.dividerTheme,g=d.jqmData("splittheme"),h=d.jqmData("spliticon"),i=d.children("li"),j=a.support.cssPseudoElement||!a.nodeName(d[0],"ol")?0:1,k,l,m,n,o,p,q,r,s,t;j&&d.find(".ui-li-dec").remove();for(s=0,t=i.length;s<t;s++){k=i.eq(s),l="ui-li";if(b||!k.hasClass("ui-li"))m=k.jqmData("theme")||c.theme,n=k.children("a"),n.length?(r=k.jqmData("icon"),k.buttonMarkup({wrapperEls:"div",shadow:!1,corners:!1,iconpos:"right",icon:!1,theme:m}),r!=0&&n.length==1&&k.addClass("ui-li-has-arrow"),n.first().addClass("ui-link-inherit"),n.length>1&&(l+=" ui-li-has-alt",o=n.last(),p=g||o.jqmData("theme")||c.splitTheme,o.appendTo(k).attr("title",o.getEncodedText()).addClass("ui-li-link-alt").empty().buttonMarkup({shadow:!1,corners:!1,theme:m,icon:!1,iconpos:!1}).find(".ui-btn-inner").append(a("<span />").buttonMarkup({shadow:!0,corners:!0,theme:p,iconpos:"notext",icon:h||o.jqmData("icon")||c.splitIcon})))):k.jqmData("role")==="list-divider"?(l+=" ui-li-divider ui-btn ui-bar-"+f,k.attr("role","heading"),j&&(j=1)):l+=" ui-li-static ui-body-"+m;j&&l.indexOf("ui-li-divider")<0&&(q=k.is(".ui-li-static:first")?k:k.find(".ui-link-inherit"),q.addClass("ui-li-jsnumbering").prepend("<span class='ui-li-dec'>"+j++ +". </span>")),k.add(k.children(".ui-btn-inner")).addClass(l),e._itemApply(d,k)}this._refreshCorners(b)},_idStringEscape:function(a){return a.replace(/\W/g,"-")},_createSubPages:function(){var b=this.element,d=b.closest(".ui-page"),e=d.jqmData("url"),f=e||d[0][a.expando],g=b.attr("id"),h=this.options,i="data-"+a.mobile.ns,j=this,k=d.find(":jqmData(role='footer')").jqmData("id"),l,m;typeof c[f]=="undefined"&&(c[f]=-1),g=g||++c[f],a(b.find("li>ul, li>ol").toArray().reverse()).each(function(c){var d=this,f=a(this),j=f.attr("id")||g+"-"+c,m=f.parent(),n,p=n.first().getEncodedText(),q=(e||"")+"&"+a.mobile.subPageUrlKey+"="+j,r=f.jqmData("theme")||h.theme,s=f.jqmData("counttheme")||b.jqmData("counttheme")||h.countTheme,t,u;n=a(f.prevAll().toArray().reverse()),n=n.length?n:a("<span>"+a.trim(m.contents()[0].nodeValue)+"</span>"),l=!0,t=f.detach().wrap("<div "+i+"role='page' "+i+"url='"+q+"' "+i+"theme='"+r+"' "+i+"count-theme='"+s+"'><div "+i+"role='content'></div></div>").parent().before("<div "+i+"role='header' "+i+"theme='"+h.headerTheme+"'><div class='ui-title'>"+p+"</div></div>").after(k?a("<div "+i+"role='footer' "+i+"id='"+k+"'>"):"").parent().appendTo(a.mobile.pageContainer),t.page(),u=m.find("a:first"),u.length||(u=a("<a/>").html(n||p).prependTo(m.empty())),u.attr("href","#"+q)}).extendablelist(),l&&d.is(":jqmData(external-page='true')")&&d.data("page").options.domCache===!1&&(m=function(b,c){var f=c.nextPage,g;c.nextPage&&(g=f.jqmData("url"),g.indexOf(e+"&"+a.mobile.subPageUrlKey)!==0&&(j.childPages().remove(),d.remove()))},d.unbind("pagehide.remove").bind("pagehide.remove",m))},childPages:function(){var b=this.parentPage.jqmData("url");return a(":jqmData(url^='"+b+"&"+a.mobile.subPageUrlKey+"')")}}),a(document).bind("pagecreate create",function(b){a(a.tizen.extendablelist.prototype.options.initSelector,b.target).extendablelist()})}(jQuery),ensureNS("jQuery.mobile.tizen.clrlib"),jQuery.extend(jQuery.mobile.tizen.clrlib,{nearestInt:function(a){var b=Math.floor(a);return a-b>.5?b+1:b},HTMLToRGB:function(a){return a="#"==a.charAt(0)?a.substring(1):a,[a.substring(0,2),a.substring(2,4),a.substring(4,6)].map(function(a){return parseInt(a,16)/255})},RGBToHTML:function(a){return"#"+a.map(function(a){var b=a*255,c=Math.floor(b);return b=b-c>.5?c+1:c,b=(b<16?"0":"")+(b&255).toString(16),b}).join("")},HSLToRGB:function(a){var b=a[0]/360,c=a[1],d=a[2];if(0===c)return[d,d,d];var e=d<.5?d*(1+c):d+c-d*c,f=2*d-e,g={r:b+1/3,g:b,b:b-1/3};return g.r=g.r<0?g.r+1:g.r>1?g.r-1:g.r,g.g=g.g<0?g.g+1:g.g>1?g.g-1:g.g,g.b=g.b<0?g.b+1:g.b>1?g.b-1:g.b,ret=[6*g.r<1?f+(e-f)*6*g.r:2*g.r<1?e:3*g.r<2?f+(e-f)*(2/3-g.r)*6:f,6*g.g<1?f+(e-f)*6*g.g:2*g.g<1?e:3*g.g<2?f+(e-f)*(2/3-g.g)*6:f,6*g.b<1?f+(e-f)*6*g.b:2*g.b<1?e:3*g.b<2?f+(e-f)*(2/3-g.b)*6:f],ret},HSVToRGB:function(a){return $.mobile.tizen.clrlib.HSLToRGB($.mobile.tizen.clrlib.HSVToHSL(a))},RGBToHSV:function(a){var b,c,d,e,f,g,h=a[0],i=a[1],j=a[2];return b=Math.min(h,Math.min(i,j)),c=Math.max(h,Math.max(i,j)),d=c-b,e=0,f=0,g=c,d>1e-5&&(f=d/c,h===c?e=(i-j)/d:i===c?e=2+(j-h)/d:e=4+(h-i)/d,e*=60,e<0&&(e+=360)),[e,f,g]},HSVToHSL:function(a){var b=a[2],c=a[1]*b,d=b-c,e=b+d,f=e/2,g=f<.5?e:2-b-d;return[a[0],0==g?0:c/g,f]},RGBToHSL:function(a){return $.mobile.tizen.clrlib.HSVToHSL($.mobile.tizen.clrlib.RGBToHSV(a))}}),function(a,b,c){a.mobile.defaultPageTransition="none",a.mobile.transitionHandlers.depth=a.mobile.transitionHandlers.simultaneous,a.mobile.transitionFallbacks.depth="fade",a.fn.buttonMarkup.defaults.corners=!1,a.mobile.buttonMarkup.hoverDelay=0}(jQuery,this),function(a,b,c,d){function e(){this.vertices=[-1,-1,0,1,-1,0,1,1,0,-1,1,0],this.textureCoords=[1,0,0,0,0,1,1,1],this.normalVectors=[0,0,1,0,0,1,0,0,1,0,0,1],this.texture=null,this.textureBuffer=null,this.textureBufferItemSize=0,this.mashOrder=[],this.mvMatrix=null,this.level=-1,this.targetLevel=0,this.drawable=!1,this.image=null,this.imageID=0}var f=!1,g={},h,i,j,k,l=function(){if(f)return;c.initGlMatrix(g),h=["attribute vec3 aVertexPosition;","attribute vec2 aTextureCoord;","attribute vec3 aVertexNormal;","uniform mat4 uMoveMatrix;","uniform mat4 uPerspectiveMatrix;","uniform mat3 nNormalMatrix;","uniform vec3 uAmbientColor;","uniform vec3 uLightDirection;","uniform vec3 uDirectionColor;","uniform vec3 uLightDirection_first;","uniform vec3 uLightDirection_second;","varying vec2 vTextureCoord;","varying vec3 vLightWeight;","varying vec4 vFogWeight;","void main(void) {","\tvec4 v_Position = uMoveMatrix * vec4(aVertexPosition, 1.0);","\tgl_Position = uPerspectiveMatrix * v_Position;","\tvTextureCoord = aTextureCoord;","\tfloat fog = 1.0 - ((gl_Position.z + 1.5) / 60.0);","\tvFogWeight = clamp( vec4( fog, fog, fog, 1.0), 0.6, 1.0);","\tvec3 transNormalVector = nNormalMatrix * aVertexNormal;","\tfloat vLightWeightFirst = 0.0;","\tfloat vLightWeightSecond = max( dot(transNormalVector, uLightDirection_second), 0.0 );","\tvLightWeight = uAmbientColor + uDirectionColor * vLightWeightSecond;","}"].join("\n"),i=["precision mediump float;","varying vec2 vTextureCoord;","varying vec3 vLightWeight;","uniform sampler2D uSampler;","varying vec4 vFogWeight;","void main(void) {","\tvec4 TextureColor;","\tif ( vTextureCoord.s <= 0.01 || vTextureCoord.s >= 0.99 || vTextureCoord.t <= 0.01 || vTextureCoord.t >= 0.99 ) {","\t\tTextureColor = vec4(1.0, 1.0, 1.0, 0.5);","\t} else {","\t\tTextureColor = texture2D(uSampler, vec2(vTextureCoord.s, vTextureCoord.t));","\t}","\tTextureColor *= vFogWeight;","\tgl_FragColor = vec4(TextureColor.rgb * vLightWeight, TextureColor.a);","}"].join("\n"),j=typeof c.Float32Array!="undefined"?c.Float32Array:typeof c.WebGLFloatArray!="undefined"?c.WebGLFloatArray:Array,k=typeof c.Uint16Array!="undefined"?c.Uint16Array:Array,f=!0},m=function(a){return a*Math.PI/180},n=function(b){var c,d,e=["experimental-webgl","webkit-3d","webgl","moz-webgl"];for(d=0;d<e.length;d+=1)try{c=b.getContext(e[d]);if(c)break}catch(f){a(b).html("Unfortunately, there's a WebGL compatibility problem. </br> You may want to check your system settings.");return}return c},o=function(a){var b=c.setTimeout(a,1e3/60);return b},p=function(a){c.clearTimeout(a)};a.widget("tizen.gallery3d",a.mobile.widget,{options:{thumbnailCache:!1},_MAX_ITEM_COUNT:28,_ANIMATION_END:999,_DURATION_DEFAULT:300,_DURATION_FIRST:1600,_VIEWPORT_WIDTH:1024,_VIEWPORT_HEIGHT:456,_DIRECTION_LEFT:-1,_DIRECTION_RIGHT:1,_gl:null,_shaderProgram:null,_positionBuffer:null,_textureCoordBuffer:null,_normalVectorBuffer:null,_nodes:null,_pMatrix:null,_animationID:0,_dragInterval:0,_startTime:0,_sumTime:0,_lightsPositionStack:[[0,0,-1],[-0.2,0,.7]],_path:null,_swipeThresholdOfBasetimeGap:a.support.touch?30:70,_swipeThresholdOfSensitivity:a.support.touch?2:10,_canvas:null,_imageList:[],_maxDrawLength:0,_firstImageNumber:0,_lastImageNumber:0,_create:function(){var b=this,c=b.element,e=b.options;l(),b._canvas=a("<canvas class='ui-gallery3d-canvas'></canvas>"),c.addClass("ui-gallery3d").append(b._canvas),b._addBehavier(),b._dragInterval=1e3/30,a.each(b.options,function(a,c){b.options[a]=d,b._setOption(a,c)})},destroy:function(){this._final(),a.mobile.widget.prototype.destroy.call(this)},_setOption:function(b,c){switch(b){case"thumbnailCache":typeof c=="string"?c=c==="true"?!0:!1:c=!!c,this._reset()}a.mobile.widget.prototype._setOption.call(this,b,c)},_init:function(b){var c=this,d=[[40,0,-48],[-12,0,-40],[24,0,-9],[-5,0,-5]],e;b=b||c._canvas;if(!b)return;c._gl=c._gl||c._initGL(b[0]);if(!c._gl)return;if(!c._imageList)return;c._shaderProgram=c._shaderProgram||c._initShader(c._gl);if(!c._shaderProgram)return;c._imageList.length>c._MAX_ITEM_COUNT&&(c._firstImageNumber=c._imageList.length-1,c._lastImageNumber=c._MAX_ITEM_COUNT-1),c._nodes=c._initBuffers(c._gl,c._shaderProgram),c._initTextures(c._gl,c._nodes),c._path=a.motionpath("bezier2d",{points:d,maxLevel:c._MAX_ITEM_COUNT});for(e=0;e<c._nodes.length;e+=1)c._path.levels[e]=c._path.levels[e+1]||0,c._nodes[e].level=e},_final:function(b){var c=this,d=c._gl;if(!d)return;b=b||c._canvas,a(c._nodes).each(function(a){var b=c._nodes[a];d.deleteTexture(b.texture),b.texture=null}),c._nodes=null,d.deleteBuffer(c._positionBuffer),c._positionBuffer=null,d.deleteBuffer(c._textureCoordBuffer),c._textureCoordBuffer=null,d.deleteBuffer(c._normalVectorBuffer),c._normalVectorBuffer=null,a.webgl.shader.deleteShaders(d),d.deleteProgram(c._shaderProgram),c._shaderProgram=null,c._gl=d=null},_addBehavier:function(){var b=this,c=b.element,d=b._canvas,e=a.support.touch?"touchstart":"mousedown",f=(a.support.touch?"touchmove":"mousemove")+".gallery3d",g=(a.support.touch?"touchend":"mouseup")+".gallery3d",h=(a.support.touch?"touchleave":"mouseout")+".gallery3d";d.on("webglcontextlost",function(a){a.preventDefault()}).on("webglcontextrestored",function(a){b._init()}).on(e,function(d){var e=0,i=0,j=20,k=[j],l=[j],m=0,n=0,o=!1,p=0;d.preventDefault(),d.stopPropagation();if(b._imageList.length<=1)return;b._stop(),i=a.support.touch?d.originalEvent.changedTouches[0].pageX:d.pageX,p=a.now();for(e=0;e<j;e+=1)k[e]=i,l[e]=a.now();m+=1,c.on(f,function(c){var d,e,f;c.preventDefault(),c.stopPropagation(),d=a.support.touch?c.originalEvent.changedTouches[0].pageX:c.pageX,e=i-d,k[m]=d,l[m]=a.now(),f=l[m]-p,m=(m+1)%j,Math.abs(e)>=10&&f>=b._dragInterval&&(o!==(e<0?b._DIRECTION_RIGHT:b._DIRECTION_LEFT)&&(n=0,o=e<0?b._DIRECTION_RIGHT:b._DIRECTION_LEFT),n+=Math.abs(e)/100,n>=1?(b._setPosition(b._ANIMATION_END,o),n=0):b._setPosition(n,o),b._drawScene(),i=d,p=a.now())}).on(g,function(d){var f=0,g=-1,h=0,p=0,q=0,r=0,s=0,t=0,u=0,v=!0,w;d.preventDefault(),d.stopPropagation(),f=a.now()-b._swipeThresholdOfBasetimeGap,s=a.support.touch?d.originalEvent.changedTouches[0].pageX:d.pageX,u=i-s,i=0;for(e=0;e<j;e+=1){h=(m+e)%j;if(l[h]>f){g=h;break}}g<0&&(v=!1);if(v){p=g;for(e=0;e<j;e+=1){p=(p-1+j)%j;if(l[p]<l[g])break}if(e===j||f<l[p])v=!1}v&&(q=(f-l[p])/(l[g]-l[p]),r=(1-q)*k[p]+q*k[g],Math.abs(r-s)<b._swipeThresholdOfSensitivity&&(r=s),t=parseInt((s-r)/(a.now()-f),10)),v&&t?(w=t<0?b._DIRECTION_LEFT:b._DIRECTION_RIGHT,b._run(w,Math.abs(t),n)):o!==0&&n&&b._animate(null,b._DURATION_DEFAULT*(1-n),o,0,n),c.unbind(".gallery3d")}).on(h,function(a){c.trigger(g)})})},_initGL:function(a){var b=this,c=g.mat4,d;return d=n(a),d?(d.enable(d.BLEND),d.blendFunc(d.SRC_ALPHA,d.ONE_MINUS_SRC_ALPHA),d.enable(d.DEPTH_TEST),d.depthFunc(d.LEQUAL),a.width=b._VIEWPORT_WIDTH,a.height=b._VIEWPORT_HEIGHT,d.viewportWidth=a.width,d.viewportHeight=a.height,d.viewport(0,0,d.viewportWidth,d.viewportHeight),b._pMatrix=c.create(),c.perspective(40,d.viewportWidth/d.viewportHeight,.1,1e4,b._pMatrix),d.clearColor(.15,.15,.15,1),d.clear(d.COLOR_BUFFER_BIT|d.DEPTH_BUFFER_BIT),d):null},_initShader:function(b){var c=this,d;return d=a.webgl.shader.addShaderProgram(c._gl,h,i),b.useProgram(d),d.vertexPositionAttr=b.getAttribLocation(d,"aVertexPosition"),b.enableVertexAttribArray(d.vertexPositionAttr),d.textureCoordAttr=b.getAttribLocation(d,"aTextureCoord"),b.enableVertexAttribArray(d.textureCoordAttr),d.vertexNormalAttr=b.getAttribLocation(d,"aVertexNormal"),b.enableVertexAttribArray(d.vertexNormalAttr),d.perspectiveMU=b.getUniformLocation(d,"uPerspectiveMatrix"),d.transformMU=b.getUniformLocation(d,"uMoveMatrix"),d.sampleUniform=b.getUniformLocation(d,"uSampler"),d.normalMU=b.getUniformLocation(d,"nNormalMatrix"),d.ambientColorU=b.getUniformLocation(d,"uAmbientColor"),d.lightDirU_first=b.getUniformLocation(d,"uLightDirection_first"),d.lightDirU_second=b.getUniformLocation(d,"uLightDirection_second"),d.directionColorU=b.getUniformLocation(d,"uDirectionColor"),d},_initBuffers:function(b,c){var d=this,f=0,g=0,h=[],i=[],l=[],m=[],n=d._MAX_ITEM_COUNT;for(f=0;f<d._imageList.length+1;f+=1)m[f]=new e,a.merge(h,m[f].vertices),a.merge(i,m[f].textureCoords),a.merge(l,m[f].normalVectors),m[f].textureBuffer=b.createBuffer(),b.bindBuffer(b.ELEMENT_ARRAY_BUFFER,m[f].textureBuffer),g=f*4,m[f].meshOrder=[g,g+1,g+2,g+2,g+3,g],b.bufferData(b.ELEMENT_ARRAY_BUFFER,new k(m[f].meshOrder),b.STATIC_DRAW),b.bindBuffer(b.ELEMENT_ARRAY_BUFFER,null),m[f].textureBufferItemSize=6;return d._positionBuffer=a.webgl.buffer.attribBufferData(b,new j(h)),d._positionBuffer.itemSize=3,d._textureCoordBuffer=a.webgl.buffer.attribBufferData(b,new j(i)),d._textureCoordBuffer.itemSize=2,d._normalVectorBuffer=a.webgl.buffer.attribBufferData(b,new j(l)),d._normalVectorBuffer.itemSize=3,b.uniform3f(c.ambientColorU,.1,.1,.1),b.uniform3f(c.directionColorU,1,1,1),m},_initTextures:function(b,c){var d=this;a(c).each(function(a){var e=c[a],f;if(!d._imageList[a])return!1;f=d._imageList[a].src,e.texture=b.createTexture(),d._loadImage(f,a,a,b,c)})},_loadImage:function(b,c,d,e,f){var g=this,h=!1,i,j;e=e||g._gl,f=f||g._nodes,h=h||!1,j=f[c],j.image=j.image||new Image,a(j.image).one("load",function(a){g._bindTexture(e,j,this,h),j.imageID=d,g._animationID||g._setPosition(0,0)}),g.options.thumbnailCache?a.imageloader.getThumbnail(b,function(c){c==="NOT_FOUND_ERR"?a.imageloader.setThumbnail(b,function(a){a&&a.length>30?(j.image.src=a,h=!0):j.image.src=b}):c&&c.length>30?(j.image.src=c,h=!0):j.image.src=b}):j.image.src=b},_bindTexture:function(a,b,c,d){if(!b||!b.texture)return;a.pixelStorei(a.UNPACK_FLIP_Y_WEBGL,!0),a.bindTexture(a.TEXTURE_2D,b.texture),a.texImage2D(a.TEXTURE_2D,0,a.RGBA,a.RGBA,a.UNSIGNED_BYTE,c),d?(a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MAG_FILTER,a.LINEAR),a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MIN_FILTER,a.LINEAR_MIPMAP_NEAREST),a.generateMipmap(a.TEXTURE_2D)):(a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MAG_FILTER,a.LINEAR),a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MIN_FILTER,a.LINEAR)),a.texParameteri(a.TEXTURE_2D,a.TEXTURE_WRAP_S,a.CLAMP_TO_EDGE),a.texParameteri(a.TEXTURE_2D,a.TEXTURE_WRAP_T,a.CLAMP_TO_EDGE),b.texture.loaded=!0,a.bindTexture(a.TEXTURE_2D,null)},_setPosition:function(a,b){var c=this,d=g.mat4,e=c._nodes,f=c._imageList,h=f.length,i=c._MAX_ITEM_COUNT,j=h>i?i:h,k=0,l=0,n=0,o=0,p=0,q=0,r=0,s=0,t=c._path,u=0;k=b>=0?j+1:j,e[l].level||(e[l].level=j);for(l=0;l<j;l+=1)e[l].mvMatrix||(e[l].mvMatrix=d.create()),b>0&&e[l].level>=j&&(e[l].level=0),q=t.levels[e[l].level],s=(e[l].level+k+b)%k,r=t.levels[s],h>i&&(b>0&&s===1&&c._firstImageNumber!==e[l].imageID?c._loadImage(f[c._firstImageNumber].src,l,c._firstImageNumber):b<0&&s===k-1&&c._lastImageNumber!==e[l].imageID&&c._loadImage(f[c._lastImageNumber].src,l,c._lastImageNumber)),d.identity(e[l].mvMatrix),d.translate(e[l].mvMatrix,[-2,-2,1]),d.rotate(e[l].mvMatrix,m(19),[1,0,0]),n=q+(r-q)*(a>1?1:a),a>=c._ANIMATION_END&&(e[l].level=s||j,n=t.levels[e[l].level]),a<c._ANIMATION_END&&b<=0&&e[l].level<1?e[l].drawable=!1:e[l].drawable=!0,a===c._ANIMATION_END&&e[l].level===1&&c.element.trigger("select",f[e[l].imageID],e[l].imageID),o=t.getPosition(n),p=t.getAngle(n),d.translate(e[l].mvMatrix,o),d.rotate(e[l].mvMatrix,p,[0,1,0]);h>i&&a>=c._ANIMATION_END&&(c._firstImageNumber=(c._firstImageNumber-b)%h,c._firstImageNumber<0&&(c._firstImageNumber=h-1),c._lastImageNumber=(c._lastImageNumber-b)%h,c._lastImageNumber<0&&(c._lastImageNumber=h-1)),c._drawScene()},_drawScene:function(){if(!this._gl||!this._shaderProgram)return;var a=this,b=a._gl,c=a._shaderProgram,d=a._nodes,e=d.length,f;b.clear(b.COLOR_BUFFER_BIT|b.DEPTH_BUFFER_BIT),b.bindBuffer(b.ARRAY_BUFFER,a._positionBuffer),b.vertexAttribPointer(c.vertexPositionAttr,a._positionBuffer.itemSize,b.FLOAT,!1,0,0),b.bindBuffer(b.ARRAY_BUFFER,a._textureCoordBuffer),b.vertexAttribPointer(c.textureCoordAttr,a._textureCoordBuffer.itemSize,b.FLOAT,!1,0,0),b.bindBuffer(b.ARRAY_BUFFER,a._normalVectorBuffer),b.vertexAttribPointer(c.vertexNormalAttr,a._normalVectorBuffer.itemSize,b.FLOAT,!1,0,0);for(f=0;f<e;f+=1)d[f].drawable&&a._drawElement(a._pMatrix,d[f])},_drawElement:function(a,b){var c=this,d=c._gl,e=g.vec3,f=g.mat3,h=g.mat4,i=c._shaderProgram,j=b.mvMatrix,k=b.texture,l=b.textureBuffer,m=b.textureBufferItemSize,n=c._lightsPositionStack,o,p;if(!j)return;d.activeTexture(d.TEXTURE0),k&&k.loaded&&d.bindTexture(d.TEXTURE_2D,k),d.uniform1i(i.sampleUniform,0),o=e.create(),e.normalize(n[0],o),e.scale(o,-8),d.uniform3fv(i.lightDirU_first,o),e.normalize(n[1],o),e.scale(o,-1),d.uniform3fv(i.lightDirU_second,o),d.bindBuffer(d.ELEMENT_ARRAY_BUFFER,l),d.uniformMatrix4fv(i.perspectiveMU,!1,a),d.uniformMatrix4fv(i.transformMU,!1,j),p=f.create(),h.toInverseMat3(j,p),f.transpose(p),d.uniformMatrix3fv(i.normalMU,!1,p),d.drawElements(d.TRIANGLES,m,d.UNSIGNED_SHORT,0),d.bindBuffer(d.ARRAY_BUFFER,null),d.bindBuffer(d.ELEMENT_ARRAY_BUFFER,null),d.bindTexture(d.TEXTURE_2D,null)},_animate:function(b,c,d,e,f,g){var h=this,i=a.now(),j,k=0;b=b||"linear",f=f||0,g=g||0;if(h._sumTime>=c){h._setPosition(h._ANIMATION_END,d),h._stop();return}if(h._startTime===0)h._startTime=i;else{h._sumTime=i-h._startTime,j=a.easing[b](h._sumTime/c,h._sumTime,f,e+1,c),k=parseInt(Math.abs(j),10);if(g!==k){h._setPosition(h._ANIMATION_END,d),g=k,e-g>=0?h._animate(b,c,d,e,f,g):h._stop();return}h._setPosition(j-g,d)}h._animationID=o(function(){h._animate(b,c,d,e,f,g)})},_run:function(a,b,c){var d=this,e=b||0,f=d._DURATION_DEFAULT*(e+1);if(d._imageList.length<=1)return;c=c||0,f=f>=0?f:0,d._animationID&&(d._setPosition(d._ANIMATION_END,a),d._stop()),d._animate("easeOutExpo",f,a,e,c)},_reset:function(){if(!this._canvas||!this._gl)return;this._final(),this._init(),this.refresh()},_stop:function(){this._animationID&&p(this._animationID),this._animationID=0,this._startTime=0,this._sumTime=0},next:function(){this
-._run(this._DIRECTION_LEFT,0)},prev:function(){this._run(this._DIRECTION_RIGHT,0)},refresh:function(){var a=this.element,b=a.find("canvas.ui-gallery3d-canvas");b.width()!==a.width()&&b.width(a.width()),this._animationID||this._setPosition(0,0)},select:function(a){var b=this._nodes,c,d,e,f=null,g=0,h=0;a&&this._animationID&&this._stop();for(d in b)if(b[d].level===1){f=this._imageList[b[d].imageID],e=b[d].imageID;break}if(!a)return f;if(a<0&&a>=this._imageList.length)return;g=a-e,h=g>0?this._DIRECTION_LEFT:g<0?this._DIRECTION_RIGHT:0,h&&this._run(h,Math.abs(g)-1)},add:function(a,b){if(!a)return;typeof a=="string"&&(a={src:a}),b=b||0;if(typeof b!="number"&&b<0&&b>=this._imageList.length)return;this._imageList.splice(b,0,a),this._gl&&this._reset()},remove:function(a){a=a||0;if(typeof a!="number"&&a<0&&a>=this._imageList.length)return;this._imageList.splice(a,1),this._gl&&this._reset()},clearThumbnailCache:function(){if(!this._nodes||this._nodes.length<=0)return;var b,c;for(b=0;b<this._imageList.length;b+=1)c=this._imageList[b].src,a.imageloader.removeThumbnail(c)},empty:function(){this._imageList=[],this._reset()},length:function(){return this._imageList.length}}),a(b).on("pagecreate create",function(b){a(":jqmData(role='gallery3d')").gallery3d()}).on("pagechange",function(b){a(b.target).find(".ui-gallery3d").gallery3d("refresh")}),a(c).on("resize orientationchange",function(b){a(".ui-page-active").find(".ui-gallery3d").gallery3d("refresh")})}(jQuery,document,window),ensureNS("jQuery.mobile.tizen"),function(){jQuery.extend(jQuery.mobile.tizen,{disableSelection:function(a){return this.enableSelection($(a).find("*").not('input, [type="text"], textarea'),"none"),!0},enableSelection:function(a,b){var c;switch(b){case"text":case"auto":case"none":c=b;break;default:c="auto"}return $(a).css({"user-select":c,"-moz-user-select":c,"-webkit-user-select":c,"-o-user-select":c,"-ms-transform":c})},disableContextMenu:function(a){var b=this;$(a).find("*").each(function(){$(this).get(0).tagName!=="INPUT"&&$(this).attr("type")!=="text"&&$(this).get(0).tagName!=="TEXTAREA"&&b._disableContextMenu(this)})},_disableContextMenu:function(a){$(a).each(function(){$(this).bind("contextmenu",function(a){return!1})})},enableContextMenu:function(a){$(a).each(function(){$(this).unbind("contextmenu")})},documentRelativeCoordsFromEvent:function(a){var b=a?a:window.event,c={x:b.clientX,y:b.clientY},d={x:b.pageX,y:b.pageY},e=0,f=0;b.type.match(/^touch/)&&(d={x:b.originalEvent.targetTouches[0].pageX,y:b.originalEvent.targetTouches[0].pageY},c={x:b.originalEvent.targetTouches[0].clientX,y:b.originalEvent.targetTouches[0].clientY});if(d.x||d.y)e=d.x,f=d.y;else if(c.x||c.y)e=c.x+document.body.scrollLeft+document.documentElement.scrollLeft,f=c.y+document.body.scrollTop+document.documentElement.scrollTop;return{x:e,y:f}},targetRelativeCoordsFromEvent:function(a){var b={x:a.offsetX,y:a.offsetY};if(b.x===undefined||isNaN(b.x)||b.y===undefined||isNaN(b.y)){var c=$(a.target).offset();b=$.mobile.tizen.documentRelativeCoordsFromEvent(a),b.x-=c.left,b.y-=c.top}return b}})}(),function(a,b){a.widget("mobile.pagelayout",a.mobile.widget,{options:{visibleOnPageShow:!0,disablePageZoom:!0,transition:"slide",fullscreen:!1,tapToggle:!0,tapToggleBlacklist:"a, input, select, textarea, .ui-header-fixed, .ui-footer-fixed",hideDuringFocus:"input, textarea, select",updatePagePadding:!0,supportBlacklist:function(){var a=window,c=navigator.userAgent,d=navigator.platform,e=c.match(/AppleWebKit\/([0-9]+)/),f=!!e&&e[1],g=c.match(/Fennec\/([0-9]+)/),h=!!g&&g[1],i=c.match(/Opera Mobi\/([0-9]+)/),j=!!i&&i[1];return(d.indexOf("iPhone")>-1||d.indexOf("iPad")>-1||d.indexOf("iPod")>-1)&&f&&f<534||a.operamini&&{}.toString.call(a.operamini)==="[object OperaMini]"||i&&j<7458||c.indexOf("Android")>-1&&f&&f<533||h&&h<6||window.palmGetResource!==b&&f&&f<534||c.indexOf("MeeGo")>-1&&c.indexOf("NokiaBrowser/8.5.0")>-1?!0:!1},initSelector:":jqmData(role='content')"},_create:function(){var a=this,b=a.options,c=a.element;if(b.supportBlacklist()){a.destroy();return}a._addFixedClass(),a._addTransitionClass(),a._bindPageEvents(),a._bindContentControlEvents(),a._backBtnQueue=[]},_addFixedClass:function(){var a=this,b=a.options,c=a.element,d=c.siblings(":jqmData(role='header')"),e=c.siblings(":jqmData(role='footer')"),f=c.closest(".ui-page");d.addClass("ui-header-fixed"),e.addClass("ui-footer-fixed"),b.fullscreen?(d.addClass("ui-header-fullscreen"),e.addClass("ui-footer-fullscreen"),f.addClass("ui-page-header-fullscreen").addClass("ui-page-footer-fullscreen")):f.addClass("ui-page-header-fixed").addClass("ui-page-footer-fixed")},_addTransitionClass:function(){var a=this.options.transition;a&&a!=="none"&&(a==="slide"&&(a=this.element.is(".ui-header")?"slidedown":"slideup"),this.element.addClass(a))},setHeaderFooter:function(b){var c=a(b),d=c.find(":jqmData(role='header')").length?c.find(":jqmData(role='header')"):c.siblings(":jqmData(role='header')"),e=c.find(".ui-content"),f=c.find(":jqmData(role='footer')"),g=f.find(":jqmData(role='fieldcontain')"),h=f.find(".ui-controlgroup");c.is(".ui-dialog")||(d.jqmData("position")=="fixed"||a.support.scrollview&&a.tizen.frameworkData.theme.match(/tizen/)?d.css("position","fixed").css("top","0px"):!a.support.scrollview&&d.jqmData("position")!="fixed"&&d.css("position","relative")),d.find("span.ui-title-text-sub").length&&d.addClass("ui-title-multiline"),g.find("div").is(".ui-controlgroup-label")&&g.find("div.ui-controlgroup-label").remove();if(h.length){var i=100/h.find("a").length;h.find("a").each(function(a){h.find("a").eq(a).width(i+"%")})}},_bindPageEvents:function(){var b=this,c=b.options,d=b.element,e;d.closest(".ui-page").bind("pagebeforeshow",function(d){var e=this;c.disablePageZoom&&a.mobile.zoom.disable(!0),c.visibleOnPageShow||b.hide(!0),b.setHeaderFooter(e),b._setContentMinHeight(e)}).bind("webkitAnimationStart animationstart updatelayout",function(a,d){var e=this;c.updatePagePadding&&(b.updatePagePadding(e),b.updatePageLayout(e,d))}).bind("pageshow",function(d){var e=this;b._setContentMinHeight(e),b.updatePagePadding(e),b._updateHeaderArea(e),c.updatePagePadding&&a(window).bind("throttledresize."+b.widgetName,function(){b.updatePagePadding(e),b.updatePageLayout(e,!1),b._updateHeaderArea(e),b._setContentMinHeight(e)})}).bind("pagebeforehide",function(d,e){c.disablePageZoom&&a.mobile.zoom.enable(!0),c.updatePagePadding&&a(window).unbind("throttledresize."+b.widgetName)}),window.addEventListener("softkeyboardchange",function(c){var d=a("<div class='ui-btn-footer-down'></div>"),e=a(".ui-page-active"),f,g="footer";e.data("addBackBtn")&&(e.data("addBackBtn")=="header"?g="header":g="footer",c.state=="on"?(e.find(".ui-"+g+" .ui-btn-footer-down").length||d.buttonMarkup({icon:"down"}).appendTo(e.find(".ui-"+g)),f=a(".ui-page-active .ui-btn-back"),f.hide(),b._backBtnQueue.push(f)):c.state=="off"&&(b._backBtnQueue.forEach(function(a){a.show()}),b._backBtnQueue.length=0,a(".ui-btn-footer-down").remove()))})},_bindContentControlEvents:function(){var a=this,b=a.options,c=a.element;c.closest(".ui-page").bind("pagebeforeshow",function(a){})},_setContentMinHeight:function(b){var c=a(b),d=c.find(":jqmData(role='header')"),e=c.find(":jqmData(role='footer')"),f=c.find(":jqmData(role='content')"),g,h=1,i=window.innerHeight;!a.support.scrollview||a.support.scrollview&&f.jqmData("scroll")==="none"?(h=window.outerWidth/window.innerWidth,i=Math.floor(window.outerHeight/h)):i=window.innerHeight,g=i-d.height()-e.height(),a.support.scrollview&&f.jqmData("scroll")!=="none"&&(f.css("min-height",g-parseFloat(f.css("padding-top"))-parseFloat(f.css("padding-bottom"))+"px"),f.children(".ui-scrollview-view").css("min-height",f.css("min-height")))},_updateHeaderArea:function(b){var c=a(b),d=c.find(":jqmData(role='header')").length?c.find(":jqmData(role='header')"):c.siblings(":jqmData(role='header')"),e=d.children("a").length,f=d.children("img").length;c.is(".ui-dialog")||d.find("h1").css("width",window.innerWidth-parseInt(d.find("h1").css("margin-left"),10)*2-d.children("a").width()*e-d.children("a").width()/4-d.children("img").width()*f*4)},_visible:!0,updatePagePadding:function(b){var c=this.element,d=c.siblings(".ui-header").length,e=c.siblings(".ui-footer").length;if(this.options.fullscreen)return;b=b||c.closest(".ui-page"),(c.siblings(".ui-header").jqmData("position")=="fixed"||a.support.scrollview&&c.jqmData("scroll")!=="none")&&a(b).css("padding-top",d?c.siblings(".ui-header").outerHeight():0),a(b).css("padding-bottom",e?c.siblings(".ui-footer").outerHeight():0)},updatePageLayout:function(b,c){var d,e=a(b),f=e.find(":jqmData(role='header')"),g=e.find(":jqmData(role='content')"),h=0,i=0,j=0,k=window.innerHeight,l=1;e.length?d=e.find(":jqmData(role='footer')"):d=a(document).find(":jqmData(role='footer')").eq(0),i=d.css("display")=="none"||d.length==0?0:d.height(),j=f.css("display")=="none"||f.length==0?0:f.height(),i!=0&&d.css("bottom",0),!a.support.scrollview||a.support.scrollview&&g.jqmData("scroll")==="none"?(l=window.outerWidth/window.innerWidth,k=Math.floor(window.outerHeight/l)):k=window.innerHeight,h=k-i-j,a.support.scrollview&&g.jqmData("scroll")!=="none"&&g.height(h-parseFloat(g.css("padding-top"))-parseFloat(g.css("padding-bottom"))),c&&e.css("min-height",h).css("padding-top",j).css("padding-bottom",i)},show:function(a){},hide:function(a){},toggle:function(){this[this._visible?"hide":"show"]()},destroy:function(){this.element.removeClass("ui-header-fixed ui-footer-fixed ui-header-fullscreen ui-footer-fullscreen in out fade slidedown slideup ui-fixed-hidden"),this.element.closest(".ui-page").removeClass("ui-page-header-fixed ui-page-footer-fixed ui-page-header-fullscreen ui-page-footer-fullscreen")},refresh:function(){var b=a(".ui-page-active");this.setHeaderFooter(b),this._updateHeaderArea(b)}}),a(document).bind("pagecreate create",function(b){a(b.target).jqmData("fullscreen")&&a(a.mobile.pagelayout.prototype.options.initSelector,b.target).not(":jqmData(fullscreen)").jqmData("fullscreen",!0),a.mobile.pagelayout.prototype.enhanceWithin(b.target)})}(jQuery),function(a,b){var c={},d=0,e=1,f=-1;a.widget("tizen.virtuallistview",a.mobile.widget,{options:{theme:"s",countTheme:"s",headerTheme:"s",dividerTheme:"s",splitIcon:"arrow-r",splitTheme:"s",inset:!1,id:"",childSelector:" li",dbtable:"",template:"",dbkey:!1,scrollview:!1,row:100,page_buf:30,initSelector:":jqmData(role='virtuallistview')"},_stylerMouseUp:function(){a(this).addClass("ui-btn-up-s"),a(this).removeClass("ui-btn-down-s")},_stylerMouseDown:function(){a(this).addClass("ui-btn-down-s"),a(this).removeClass("ui-btn-up-s")},_stylerMouseOver:function(){a(this).toggleClass("ui-btn-hover-s")},_stylerMouseOut:function(){a(this).toggleClass("ui-btn-hover-s"),a(this).addClass("ui-btn-up-s"),a(this).removeClass("ui-btn-down-s")},_pushData:function(b){var c=this.options,d,e=a("#"+b),f=c.row>this._numItemData?this._numItemData:c.row,g;for(d=0;d<f;d++)g=e.tmpl(this._itemData(d)),a(c.id).append(a(g).attr("id",c.itemIDPrefix+d));a(c.id).trigger("create")},_reposition:function(b){var c,d=this,e,f;b.data?c=b.data:c=b,a(c.id+c.childSelector).size()>0&&(d._title_h=a(c.id+c.childSelector+":first").position().top,d._line_h=a(c.id+c.childSelector+":first").outerHeight(),d._container_w=a(c.id).innerWidth(),e=parseInt(a(c.id+c.childSelector).css("padding-left"),10)+parseInt(a(c.id+c.childSelector).css("padding-right"),10),a(c.id+">"+c.childSelector).addClass("position_absolute").addClass("ui-btn-up-s").bind("mouseup",d._stylerMouseUp).bind("mousedown",d._stylerMouseDown).bind("mouseover",d._stylerMouseOver).bind("mouseout",d._stylerMouseOut)),a(c.id+">"+c.childSelector).each(function(b){f=parseInt(a(this).css("margin-left"),10)+parseInt(a(this).css("margin-right"),10),a(this).css("top",d._title_h+d._line_h*b+"px").css("width",d._container_w-e-f)}),a(c.id).height(d._numItemData*d._line_h)},_resize:function(b){var c,d=this,e,f,g;b.data?c=b.data:c=b,e=a(c).children(c.childSelector),d._container_w=a(c).width(),f=parseInt(e.css("padding-left"),10)+parseInt(e.css("padding-right"),10),e.each(function(b,c){g=parseInt(a(this).css("margin-left"),10)+parseInt(a(this).css("margin-right"),10),a(this).css("width",d._container_w-f-g)})},_scrollmove:function(b){function j(){return d.scrollview?h.viewTop():i.viewTop()}function k(a){var b=!1;b&&console.log(">>virtualllist: "+a)}function l(b,c){function t(b,c,d){var e={ELEMENT_NODE:1,TEXT_NODE:3},f,g,h,i,j;a(c).find(".ui-li-text-main",".ui-li-text-sub",".ui-li-text-sub2","ui-btn-text").each(function(b){f=a(this),h=a(d).find(".ui-li-text-main",".ui-li-text-sub","ui-btn-text").eq(b).text(),a(f).contents().filter(function(){return this.nodeType==e.TEXT_NODE}).get(0).data=h}),a(c).find("img").each(function(b){var c=a(this);i=a(d).find("img").eq(b).attr("src"),a(c).attr("src",i)}),a(c).removeData()}function u(b,c,d){var e,f,g,h;return k(">> move item: "+c+" --> "+d),f=a("#"+b.options.itemIDPrefix+c),!f||!f.length?!1:(h=a("#"+b.options.template),h&&(g=h.tmpl(b._itemData(d)),t(b,f,g),g.remove()),f.css("top",d*b._line_h).attr("id",b.options.itemIDPrefix+d),!0)}var d,e,g,h=b._first_index,i=b._last_index,m,n,o,p,q=b.options.row,r,s;d=j(),r=Math.ceil(q/3),e=Math.floor(d/b._line_h)-r,g=e+q-1,e<0?(g+=-e,e=0):g>b._numItemData-1&&(e-=g-(b._numItemData-1),g=b._numItemData-1),m=e-h,k("cy="+d+", oti="+h+", obi="+i+", cti="+e+", cbi="+g+", dti="+m);if(0==m){b.timerStillCount+=1;if(b.timerStillCount<12){k("dti=0 "+b.timerStillCount+" times"),b.timerMoveID=setTimeout(l,f,b);return}k("dti=0 "+b.timerStillCount+" times. End timer."),b.timerStillCount=0,b.timerMoveID&&(clearTimeout(b.timerMoveID),b.timerMoveID=null)}else{b.timerStillCount=0,Math.abs(m)>=q?(n=h,o=i,p=m,k(">>> WHOLE CHANGE! delta="+p)):(m>0?(n=h,o=h+m-1,p=q):(n=i+m+1,o=i,p=-q),k(">>> partial change. delta="+p));for(s=n;s<=o;s++)u(b,s,s+p);b._first_index=e,b._last_index=g,b.timerMoveID=setTimeout(l,f,b)}return}var c=b.data,d=c.options,e=c._num_top_items,f=100,g,h,i;h={viewTop:function(){var b=a(d.id).parentsUntil(".ui-page").find(".ui-scrollview-view"),c=b.css("-webkit-transform"),e="0,0,0,0,0,0";return c&&(e=c.replace(/matrix\s*\((.*)\)/,"$1")),-parseInt(e.split(",")[5],10)}},i={viewTop:function(){return a(window).scrollTop()}},c.timerStillCount=0,c.timerMoveID&&(clearTimeout(c.timerMoveID),c.timerMoveID=null),l(c)},_recreate:function(b){var c=this,e=this.options;a(e.id).empty(),c._numItemData=b.length,c._direction=d,c._first_index=0,c._last_index=e.row-1,c._pushData(e.template),e.childSelector==" ul"&&a(e.id+" ul").swipelist(),a(e.id).virtuallistview(),c.refresh(!0),c._reposition(e)},_initList:function(){var b=this,c=this.options;b._pushData(c.template),a(c.id).parentsUntil(".ui-page").parent().one("pageshow",function(){setTimeout(function(){b._reposition(c)},0)}),a(document).bind("scrollstart.virtuallist scrollstop.vrituallist",b,b._scrollmove),a(window).on("throttledresize",a(c.id),b._resize),c.childSelector==" ul"&&a(c.id+" ul").swipelist(),b.refresh(!0)},create:function(){var a=this.options;this._create.apply(this,arguments),this._reposition(a)},_create:function(b){a.extend(this,{_itemData:function(a){return null},_numItemData:0,_cacheItemData:function(a,b){},_title_h:0,_container_w:0,_minimum_row:100,_direction:d,_first_index:0,_last_index:0,_num_top_items:0});var c=this,e=this.options,f=this.element,g=a('<div class="ui-virtuallist"/>'),h=a("<ul></ul>"),i=f.find(':jqmData(role="virtuallistview" )'),j=null,k=this,l,m;f.addClass(function(a,b){return b+" ui-listview ui-virtual-list-container"+(c.options.inset?" ui-listview-inset ui-corner-all ui-shadow ":"")}),e.itemIDPrefix=f.attr("id")+"_",e.id="#"+f.attr("id"),a(e.id).bind("pagehide",function(b){a(e.id).empty()}),a(".ui-scrollview-clip").size()>0?e.scrollview=!0:e.scrollview=!1,f.data("row")&&(e.row=f.data("row"),e.row<c._minimum_row&&(e.row=c._minimum_row),e.page_buf=parseInt(e.row/2,10));if(b){if(!b.itemData||typeof b.itemData!="function")return;c._itemData=b.itemData;if(!b.numItemData)return;if(typeof b.numItemData=="function")c._numItemData=b.numItemData();else{if(typeof b.numItemData!="number")return;c._numItemData=b.numItemData}}else{console.warn("WARNING: The data interface of virtuallist is changed. \nOld data interface(data-dbtable) is still supported, but will be removed in next version. \nPlease fix your code soon!");if(!a(e.id).hasClass("vlLoadSuccess"))return;l=f.jqmData("dbtable"),m=window[l],a(e.id).empty(),m||(m={}),c._itemData=function(a){return m[a]},c._numItemData=m.length}f.data("template")&&(e.template=f.data("template"),f.data("swipelist")==1?e.childSelector=" ul":e.childSelector=" li"),f.data("dbkey")&&(e.dbkey=f.data("dbkey")),c._first_index=0,c._last_index=e.row-1,c._initList()},destroy:function(){var b=this.options;a(document).unbind("scrollstop"),a(window).off("throttledresize",this._resize),a(b.id).empty(),this.timerMoveID&&(clearTimeout(this.timerMoveID),this.timerMoveID=null)},_itemApply:function(b,c){var d=c.find(".ui-li-count");d.length&&c.addClass("ui-li-has-count"),d.addClass("ui-btn-up-"+(b.jqmData("counttheme")||this.options.countTheme)+" ui-btn-corner-all"),c.find("h1, h2, h3, h4, h5, h6").addClass("ui-li-heading").end().find("p, dl").addClass("ui-li-desc").end().find(">img:eq(0), .ui-link-inherit>img:eq(0)").addClass("ui-li-thumb").each(function(){c.addClass(a(this).is(".ui-li-icon")?"ui-li-has-icon":"ui-li-has-thumb")}).end().find(".ui-li-aside").each(function(){var b=a(this);b.prependTo(b.parent())})},_removeCorners:function(a,b){var c="ui-corner-top ui-corner-tr ui-corner-tl",d="ui-corner-bottom ui-corner-br ui-corner-bl";a=a.add(a.find(".ui-btn-inner, .ui-li-link-alt, .ui-li-thumb")),b==="top"?a.removeClass(c):b==="bottom"?a.removeClass(d):a.removeClass(c+" "+d)},_refreshCorners:function(a){var b,c,d,e;this.options.inset&&(b=this.element.children("li"),c=a?b.not(".ui-screen-hidden"):b.filter(":visible"),this._removeCorners(b),d=c.first().addClass("ui-corner-top"),d.add(d.find(".ui-btn-inner")).find(".ui-li-link-alt").addClass("ui-corner-tr").end().find(".ui-li-thumb").not(".ui-li-icon").addClass("ui-corner-tl"),e=c.last().addClass("ui-corner-bottom"),e.add(e.find(".ui-btn-inner")).find(".ui-li-link-alt").addClass("ui-corner-br").end().find(".ui-li-thumb").not(".ui-li-icon").addClass("ui-corner-bl"))},refresh:function(b){this.parentPage=this.element.closest(".ui-page"),this._createSubPages();var c=this.options,d=this.element,e=this,f=d.jqmData("dividertheme")||c.dividerTheme,g=d.jqmData("splittheme"),h=d.jqmData("spliticon"),i=d.children("li"),j=a.support.cssPseudoElement||!a.nodeName(d[0],"ol")?0:1,k,l,m,n,o,p,q,r,s,t,u;j&&d.find(".ui-li-dec").remove();for(s=0,t=i.length;s<t;s++){k=i.eq(s),l="ui-li";if(b||!k.hasClass("ui-li"))u=k.jqmData("theme")||c.theme,n=k.children("a"),n.length?(r=k.jqmData("icon"),k.buttonMarkup({wrapperEls:"div",shadow:!1,corners:!1,iconpos:"right",icon:!1,theme:u}),r!=0&&n.length==1&&k.addClass("ui-li-has-arrow"),n.first().addClass("ui-link-inherit"),n.length>1&&(l+=" ui-li-has-alt",o=n.last(),p=g||o.jqmData("theme")||c.splitTheme,o.appendTo(k).attr("title",o.getEncodedText()).addClass("ui-li-link-alt").empty().buttonMarkup({shadow:!1,corners:!1,theme:u,icon:!1,iconpos:!1}).find(".ui-btn-inner").append(a("<span />").buttonMarkup({shadow:!0,corners:!0,theme:p,iconpos:"notext",icon:h||o.jqmData("icon")||c.splitIcon})))):k.jqmData("role")==="list-divider"?(l+=" ui-li-divider ui-btn ui-bar-"+f,k.attr("role","heading"),j&&(j=1)):l+=" ui-li-static ui-body-"+u;j&&l.indexOf("ui-li-divider")<0&&(q=k.is(".ui-li-static:first")?k:k.find(".ui-link-inherit"),q.addClass("ui-li-jsnumbering").prepend("<span class='ui-li-dec'>"+j++ +". </span>")),k.add(k.children(".ui-btn-inner")).addClass(l),e._itemApply(d,k)}this._refreshCorners(b)},_idStringEscape:function(a){return a.replace(/\W/g,"-")},_createSubPages:function(){var b=this.element,d=b.closest(".ui-page"),e=d.jqmData("url"),f=e||d[0][a.expando],g=b.attr("id"),h=this.options,i="data-"+a.mobile.ns,j=this,k=d.find(":jqmData(role='footer')").jqmData("id"),l,m;typeof c[f]=="undefined"&&(c[f]=-1),g=g||++c[f],a(b.find("li>ul, li>ol").toArray().reverse()).each(function(c){var d=this,f=a(this),j=f.attr("id")||g+"-"+c,m=f.parent(),n,p=n.first().getEncodedText(),q=(e||"")+"&"+a.mobile.subPageUrlKey+"="+j,r=f.jqmData("theme")||h.theme,s=f.jqmData("counttheme")||b.jqmData("counttheme")||h.countTheme,t,u;n=a(f.prevAll().toArray().reverse()),n=n.length?n:a("<span>"+a.trim(m.contents()[0].nodeValue)+"</span>"),l=!0,t=f.detach().wrap("<div "+i+"role='page' "+i+"url='"+q+"' "+i+"theme='"+r+"' "+i+"count-theme='"+s+"'><div "+i+"role='content'></div></div>").parent().before("<div "+i+"role='header' "+i+"theme='"+h.headerTheme+"'><div class='ui-title'>"+p+"</div></div>").after(k?a("<div "+i+"role='footer' "+i+"id='"+k+"'>"):"").parent().appendTo(a.mobile.pageContainer),t.page(),u=m.find("a:first"),u.length||(u=a("<a/>").html(n||p).prependTo(m.empty())),u.attr("href","#"+q)}).virtuallistview(),l&&d.is(":jqmData(external-page='true')")&&d.data("page").options.domCache===!1&&(m=function(b,c){var f=c.nextPage,g;c.nextPage&&(g=f.jqmData("url"),g.indexOf(e+"&"+a.mobile.subPageUrlKey)!==0&&(j.childPages().remove(),d.remove()))},d.unbind("pagehide.remove").bind("pagehide.remove",m))},childPages:function(){var b=this.parentPage.jqmData("url");return a(":jqmData(url^='"+b+"&"+a.mobile.subPageUrlKey+"')")}}),a(document).bind("pagecreate create",function(b){a(a.tizen.virtuallistview.prototype.options.initSelector,b.target).virtuallistview()})}(jQuery),function(a,b,c,d){function f(a,b){a.tizen||(a.tizen={}),a.tizen.frameworkData=b.frameworkData,a.tizen.loadCustomGlobalizeCulture=b.loadCustomGlobalizeCulture,a.tizen.loadTheme=b.loadTheme,a.tizen.__tizen__=b}var e={libFileName:"tizen-web-ui-fw(.min)?.js",frameworkData:{rootDir:"/usr/lib/tizen-web-ui-fw",version:"0.1",theme:"tizen-white",viewportWidth:"device-width",viewportScale:!1,defaultFontSize:22,minified:!1,debug:!1},log:{debug:function(a){e.frameworkData.debug&&console.log(a)},warn:function(a){console.warn(a)},error:function(a){console.error(a)},alert:function(a){c.alert(a)}},util:{loadScriptSync:function(b,c,d){a.ajax({url:b,dataType:"script",async:!1,crossDomain:!1,success:c,error:function(c,f,g){if(d)d(c,f,g);else{var h=[404],i="Error while loading "+b+"\n"+c.status+":"+c.statusText;-1==a.inArray(c.status,h)?e.log.alert(i):e.log.warn(i)}}})},isMobileBrowser:function(){var a=c.navigator.appVersion.indexOf("Mobile"),b=-1<a;return b}},css:{cacheBust:document.location.href.match(/debug=true/)?"?cacheBust="+(new Date).getTime():"",addElementToHead:function(b){var c=document.getElementsByTagName("head")[0];c&&a(c).prepend(b)},makeLink:function(a){var b=document.createElement("link");return b.setAttribute("rel","stylesheet"),b.setAttribute("href",a),b.setAttribute("name","tizen-theme"),b},load:function(a){var b=document.getElementsByTagName("head")[0],c=b.getElementsByTagName("link"),d,f=null;for(d=0;d<c.length;d++){if(c[d].getAttribute("rel")!="stylesheet")continue;if(c[d].getAttribute("name")=="tizen-theme"||c[d].getAttribute("href")==a){f=c[d];break}}f?f.getAttribute("href")==a?e.log.warn("Theme is already loaded. Skip theme loading in the framework."):f.setAttribute("href",a):this.addElementToHead(this.makeLink(a))}},getParams:function(){function j(){var a=navigator.theme?navigator.theme.split(":")[0]:null;return a&&(a=a.replace("-hd",""),a.match(/^tizen-/)||(a="tizen-"+a)),a}var a=document.getElementsByTagName("script"),b=null,c=!1,e,f,g,h,i;for(e in a){f=a[e],g=f.src?f.getAttribute("src"):d;if(g&&g.match(this.libFileName)){h=g.split(/[\/\\]/),i=-3,this.frameworkData.rootDir=(f.getAttribute("data-framework-root")||h.slice(0,h.length+i).join("/")||this.frameworkData.rootDir).replace(/^file:(\/\/)?/,""),this.frameworkData.version=f.getAttribute("data-framework-version")||h[h.length+i]||this.frameworkData.version,this.frameworkData.theme=f.getAttribute("data-framework-theme")||j()||this.frameworkData.theme,this.frameworkData.viewportWidth=f.getAttribute("data-framework-viewport-width")||this.frameworkData.viewportWidth,this.frameworkData.viewportScale="true"===f.getAttribute("data-framework-viewport-scale")?!0:this.frameworkData.viewportScale,this.frameworkData.minified=g.search(/\.min\.js$/)>-1?!0:!1,this.frameworkData.debug="true"===f.getAttribute("data-framework-debug")?!0:this.frameworkData.debug,c=!0;break}}return c},loadTheme:function(a){var b,c,d;a||(a=e.frameworkData.theme),b=e.frameworkData.rootDir+"/"+e.frameworkData.version+"/themes/"+a,d=b+"/theme.js",e.frameworkData.minified?c=b+"/tizen-web-ui-fw-theme.min.css":c=b+"/tizen-web-ui-fw-theme.css",e.css.load(c),e.util.loadScriptSync(d)},loadGlobalizeCulture:function(b,d){function j(b){var d=b||a("html").attr("lang")||c.navigator.language.split(".")[0]||c.navigator.userLanguage||"en",e=null,f=d.lastIndexOf("-"),g=["Cyrl","Latn","Mong"];return f!=-1&&(e=d.substr(f+1),g.join("-").indexOf(e)<0&&(d=[d.substr(0,f),e.toUpperCase()].join("-"))),d=d=="en"?"en-US":d,d}function k(a){var b=a.lastIndexOf("-"),c;return b!=-1&&(c=a.substr(0,b)),c}function l(a,b){var c=null;return"string"!=typeof a?null:(b&&b[a]?c=b[a]:c=[f.frameworkData.rootDir,f.frameworkData.version,"js","cultures",["globalize.culture.",a,".js"].join("")].join("/"),c)}function m(a,b){e.log.error("Error "+b.status+": "+b.statusText+"::Culture file ("+a+") is failed to load.")}function n(b,c){function d(){e.log.debug("Culture file ("+b+") is loaded successfully.")}function f(a,d,e){c?c(a,d,e):m(b,a)}b?a.ajax({url:b,dataType:"script",cache:!0,async:!1,success:d,error:f}):(i={status:404,statusText:"Not Found"},f(i,null,null))}var f=this,g,h,i;return h=j(b),g=l(h,d),n(g,function(a,b,c){if(a.status==404){var e=k(h),f=l(e,d);n(f,null)}else m(g,a)}),h},setGlobalize:function(){var a=this.loadGlobalizeCulture();b.culture(a)},loadCustomGlobalizeCulture:function(a){e.loadGlobalizeCulture(null,a)},setViewport:function(b){var c=null,d,f;return a("meta[name=viewport]").each(function(){c=this;return}),c?(f=a(c).prop("content"),b=f.replace(/.*width=(device-width|\d+)\s*,?.*$/gi,"$1"),e.log.warn("Viewport is set to '"+b+"' in a meta tag. Framework skips viewport setting.")):(c=document.createElement("meta"),c&&(c.name="viewport",f="width="+b+", user-scalable=no",!!isNaN(b),c.content=f,e.log.debug(f),d=document.getElementsByTagName("head").item(0),d.insertBefore(c,d.firstChild))),b},scaleBaseFontSize:function(b,c){e.log.debug("themedefaultfont size: "+b+", ratio: "+c);var d=Math.max(Math.floor(b*c),4);a("html").css({"font-size":d+"px"}),e.log.debug("html:font size is set to "+d),a(document).ready(function(){a(".ui-mobile").children("body").css({"font-size":d+"px"})})},setScaling:function(){var b=this.frameworkData.viewportWidth,d=this.frameworkData.defaultFontSize,f=1;a("body").attr("data-tizen-theme-default-font-size",d);if(!e.util.isMobileBrowser())return;this.frameworkData.viewportScale==1&&(b="screen-width"),"screen-width"==b&&(c.self==c.top?b=c.outerWidth:b=document.documentElement.clientWidth),b=this.setViewport(b),b!="device-width"&&(f=parseFloat(b/this.frameworkData.defaultViewportWidth),this.scaleBaseFontSize(d,f))}};f(a,e),e.getParams(),e.loadTheme(),e.setScaling(),e.setGlobalize(),a.mobile.autoInitializePage=!1,a(document).ready(function(){a.mobile.initializePage()})}(jQuery,window.Globalize,window),function(a,b){a.widget("tizen.notification",a.mobile.widget,{btn:null,text_bg:[],icon_img:[],interval:null,seconds:null,running:!1,_get_text:function(){var b=new Array(2);return this.type==="ticker"?(b[0]=a(this.text_bg[0]).text(),b[1]=a(this.text_bg[1]).text()):b[0]=a(this.text_bg[0]).text(),b},_set_text:function(b,c){var d=function(a,b){if(!b)return;a.text(b)};this.type==="ticker"?(d(a(this.text_bg[0]),b),d(a(this.text_bg[1]),c)):d(a(this.text_bg[0]),b)},text:function(a,b){if(a===undefined&&b===undefined)return this._get_text();this._set_text(a,b)},icon:function(b){if(b===undefined)return;this.icon_img.detach(),this.icon_img=a("<img src='"+b+"' class='ui-ticker-icon'>"),a(this.element).find(".ui-ticker").append(this.icon_img)},_refresh:function(){var b=this._get_container();a(b).addClass("fix").removeClass("show").removeClass("hide"),this._set_interval()},open:function(){var b=this._get_container();if(this.running){this._refresh();return}a(b).addClass("show").removeClass("hide").removeClass("fix"),this.running=!0,this.type==="popup"&&this._set_position(),this._set_interval()},close:function(){var b=this._get_container();if(!this.running)return;a(b).addClass("hide").removeClass("show").removeClass("fix"),this.running=!1,clearInterval(this.interval)},destroy:function(){var b=this._get_container();a(b).removeClass("show").removeClass("hide").removeClass("fix"),this._del_event(),this.running=!1},_get_container:function(){return this.type==="ticker"?a(this.element).find(".ui-ticker"):a(this.element).find(".ui-smallpopup")},_set_interval:function(){var a=this;clearInterval(this.interval),this.seconds!==undefined&&this.second!==0&&(this.interval=setInterval(function(){a.close()},this.seconds))},_add_event:function(){var a=this,b=this._get_container();this.type==="ticker"&&(b.find(".ui-ticker-btn").append(this.btn).trigger("create"),this.btn.bind("vmouseup",function(){a.close()})),b.bind("vmouseup",function(){a.close()})},_del_event:function(){var a=this._get_container();this.type==="ticker"&&this.btn.unbind("vmouseup"),a.unbind("vmouseup"),clearInterval(this.interval)},_set_position:function(){var b=this._get_container(),c=a(".ui-page-active").children(".ui-footer"),d=c.outerHeight()||0;b.css("bottom",d)},_create:function(){var c=this,d=a(this.element),e;this.btn=a('<div data-role="button" data-inline="true">Close</div>'),this.seconds=d.jqmData("interval"),this.type=d.jqmData("type")||"popup";if(this.type==="ticker"){d.wrapInner("<div class='ui-ticker'></div>"),d.find(".ui-ticker").append("<div class='ui-ticker-body'></div><div class='ui-ticker-btn'></div>"),this.text_bg=d.find("p");if(this.text_bg.length<2)d.find(".ui-ticker").append("<p></p><p></p>"),this.text_bg=d.find("p");else if(this.text_bg.length>2)for(e=2;e<this.text_bg.length;e++)a(this.text_bg[e]).css("display","none");a(this.text_bg[0]).addClass("ui-ticker-text1-bg"),a(this.text_bg[1]).addClass("ui-ticker-text2-bg"),this.icon_img=d.find("img");if(this.icon_img.length){a(this.icon_img).addClass("ui-ticker-icon");for(e=1;e<this.icon_img.length;e++)a(this.icon_img[e]).css("display","none")}}else{d.wrapInner("<div class='ui-smallpopup'></div>"),this.text_bg=d.find("p").addClass("ui-smallpopup-text-bg");if(this.text_bg.length<1)d.find(".ui-smallpopup").append("<p class='ui-smallpopup-text-bg'></p>"),this.text_bg=d.find("p");else if(this.text_bg.length>1)for(e=1;e<this.text_bg.length;e++)a(this.text_bg[e]).css("display","none");this._set_position()}this._add_event(),a(b).bind("resize",function(){if(!c.running)return;c._refresh(),c.type==="popup"&&c._set_position()})}}),a(document).bind("pagecreate create",function(b){a(b.target).find(":jqmData(role='notification')").notification()}),a(document).bind("pagebeforehide",function(b){a(b.target).find(":jqmData(role='notification')").notification("destroy")})}(jQuery,this),function(a,b,c){a.widget("tizen.tizenslider",a.mobile.widget,{options:{popup:!0},popup:null,handle:null,handleText:null,_create:function(){this.currentValue=null,this.popupVisible=!1;var b=this,d=a(this.element),e,f,g,h,i,j,k,l,m,n,o;d.slider(),d.hide(),b.popup=a('<div class="ui-slider-popup"></div>'),g=d.jqmData("popup"),g!==c&&(b.options.popup=g==1),e=d.next(".ui-slider"),h=d.attr("data-icon"),e.wrap('<div class="ui-slider-container"></div>'),b.handle=e.find(".ui-slider-handle"),e.removeClass("ui-btn-corner-all"),e.find("*").removeClass("ui-btn-corner-all");switch(h){case"bright":case"volume":l=a('<div class="ui-slider-left-'+h+'"></div>'),m=a('<div class="ui-slider-right-'+h+'"></div>'),e.before(l),e.after(m),n=l.width()+16,o=m.width()+16;break;case"text":j=d.attr("data-text-left")===c?"":d.attr("data-text-left").substring(0,3),i=d.attr("data-text-right")===c?"":d.attr("data-text-right").substring(0,3),k=Math.max(j.length,i.length)+1,n=k+"rem",o=k+"rem",l=a('<div class="ui-slider-left-text" style="left:'+ -k+"rem; width:"+k+'rem;">'+'<span style="position:relative;top:0.4em;">'+j+"</span></div>"),m=a('<div class="ui-slider-right-text" style="right:'+ -k+"rem; width:"+k+'rem;">'+'<span style="position:relative;top:0.4em;">'+i+"</span></div>"),e.before(l),e.after(m)}h&&e.parent(".ui-slider-container").css({"margin-left":n,"margin-right":o}),e.append(a('<div class="ui-slider-handle-press"></div>')),b.handle_press=e.find(".ui-slider-handle-press"),b.handle_press.css("display","none"),e.parents(".ui-page").append(b.popup),b.popup.hide(),b.handleText=e.find
-(".ui-btn-text"),b.updateSlider(),this.element.bind("change",function(){b.updateSlider()}),b.handle.bind("vmousedown",function(){b.showPopup()}),e.add(document).bind("vmouseup",function(){b.hidePopup()})},_handle_press_show:function(){this.handle_press.css("display","")},_handle_press_hide:function(){this.handle_press.css("display","none")},positionPopup:function(){var a=this.handle.offset();this.popup.offset({left:a.left+(this.handle.width()-this.popup.width())/2,top:a.top-this.popup.height()}),this.handle_press.offset({left:a.left,top:a.top})},updateSlider:function(){var a,b,c,d,e,f=function(a){var b=Math.abs(a),c;return b>999?c=4:b>99?c=3:b>9?c=2:c=1,a<0&&c++,c};this.handle.removeAttr("title"),e=this.element.val(),b=f(e);if(this.popupVisible){this.positionPopup();switch(b){case 1:case 2:a="1.5rem",d="0.15rem";break;case 3:a="1rem",d="0.5rem";break;default:a="0.8rem",d="0.5rem"}this.popup.css({"font-size":a,"padding-top":d})}if(e===this.currentValue)return;switch(b){case 1:a="0.95rem",c="0";break;case 2:a="0.85rem",c="-0.01rem";break;case 3:a="0.65rem",c="-0.05rem";break;default:a="0.45rem",c="-0.15rem"}a!=this.handleText.css("font-size")&&this.handleText.css({"font-size":a,top:c}),this.currentValue=e,this.handleText.text(e),this.popup.html(e),this.element.trigger("update",e)},showPopup:function(){if(!this.options.popup||this.popupVisible)return;this.popup.show(),this.popupVisible=!0,this._handle_press_show()},hidePopup:function(){if(!this.options.popup||!this.popupVisible)return;this.popup.hide(),this.popupVisible=!1,this._handle_press_hide()},_setOption:function(a,b){var c=b!==this.options[a];if(!c)return;switch(a){case"popup":this.options.popup=b,this.options.popup?this.updateSlider():this.hidePopup()}}}),a(document).bind("pagebeforecreate",function(d){a.data(b,"jqmSliderInitSelector")===c&&(a.data(b,"jqmSliderInitSelector",a.mobile.slider.prototype.options.initSelector),a.mobile.slider.prototype.options.initSelector=null)}),a(document).bind("pagecreate create",function(c){var d=a.data(b,"jqmSliderInitSelector");a(c.target).find(d).each(function(){var b=a(this);b.is("select")?b.slider():b.tizenslider()})})}(jQuery,this),function(a,b,c){a.tizen.scrollview.prototype.options.handler=!1,a.tizen.scrollview.prototype.options.handlerTheme="s";var d=a.tizen.scrollview.prototype._setOption,e=function(d){var e=d,f='<div class="ui-handler ui-handler-direction-',g='"><div class="ui-handler-track"><div class="ui-handler-thumb"></div></div></div>',h=e.data("scrollview"),i=h.options,j=i.direction,k=a.mobile.getInheritedTheme(h,"s"),l=i.theme||k,m=h.options.direction==="x",n=h._$view,o=h._$clip,p=e.find(".ui-scrollbar"),q=null,r=null,s=0,t=0,u=0,v=0,w=0,x,y=a.support.touch,z=(y?"touchstart":"mousedown")+".handler",A=(y?"touchmove":"mousemove")+".handler",B=(y?"touchend":"mouseup")+".handler",C=(y?" touchleave":" mouseleave")+".handler",D=function(){t=m?o.width():o.height(),s=(m?n.width():n.height())-t,w=t-u-v*2},E=function(a){var b=Math.round((m?a.x:a.y)/s*w);r[0].style[m?"left":"top"]=b+"px"},F=function(){a(b).unbind(".handler"),e.moveData=null,n.trigger("scrollstop")};if(e.find(".ui-handler-thumb").length!==0||typeof j!="string")return;q=a([f,j,g].join("")).appendTo(e.addClass(" ui-handler-"+l)),r=e.find(".ui-handler-thumb").attr({tabindex:"0","aria-label":m?"Horizontal handler, double tap and move to scroll":"Verticalhandler, double tap and move to scroll"}).hide(),u=m?r.width():r.height(),v=m?parseInt(q.css("right"),10):parseInt(q.css("bottom"),10),a.extend(e,{moveData:null}),r.bind(z,{e:r[0]},function(c){h._stopMScroll();var d=c.data.e,f=y?c.originalEvent.targetTouches[0]:c;d.style.opacity=1,e.moveData={target:d,X:parseInt(d.style.left,10)||0,Y:parseInt(d.style.top,10)||0,pX:f.pageX,pY:f.pageY},D(),n.trigger("scrollstart"),y||c.preventDefault(),a(b).bind(A,function(a){var b=e.moveData,c=b.target,d=0,f=0,g=y?a.originalEvent.targetTouches[0]:a;d=m?b.X+g.pageX-b.pX:b.Y+g.pageY-b.pY,d<0&&(d=0),d>w&&(d=w),f=-Math.round(d/w*s),m?(h._setScrollPosition(f,0),c.style.left=d+"px"):(h._setScrollPosition(0,f),c.style.top=d+"px"),a.preventDefault()}).bind(B+C,function(a){F()})}),n.bind(B,function(a){F()}),e.bind("scrollstart",function(a){if(!h.enableHandler())return;D();if(s<0||t<u){p.is(":hidden")&&p.show();return}p.is(":visible")&&p.hide(),x&&(clearInterval(x),x=c),q.addClass("ui-handler-visible"),r.stop(!0,!0).fadeIn()}).bind("scrollupdate",function(a,b){if(!h.enableHandler()||s<0||t<u)return;E(h.getScrollPosition())}).bind("scrollstop",function(a){if(!h.enableHandler()||s<0||t<u)return;x=setInterval(function(){E(h.getScrollPosition()),h._gesture_timer||(clearInterval(x),x=c)},10),h._handlerTimer&&(clearTimeout(h._handlerTimer),h._handlerTimer=0),h._handlerTimer=setTimeout(function(){h._timerID===0&&e.moveData===null&&(r.stop(!0,!0).css("opacity",1).fadeOut(function(){q.removeClass("ui-handler-visible")}),h._handlerTimer=0)},1e3)}).bind("mousewheel",function(a){q.removeClass("ui-handler-visible"),E(h.getScrollPosition())})};a.extend(a.tizen.scrollview.prototype,{enableHandler:function(a){if(typeof a=="undefined")return this.options.handler;this.options.handler=!!a;var b=this.element;this.options.handler?(b.find(".ui-handler").length===0&&e(b),b.find(".ui-scrollbar").hide(),b.find(".ui-handler").show()):(b.find(".ui-handler").removeClass("ui-handler-visible").hide(),b.find(".ui-scrollbar").show())},_setHandlerTheme:function(a){if(!a)return;var b="ui-handler-"+this.options.handlerTheme,c="ui-handler-"+a;this.element.removeClass(b).addClass(c),this.options.handlerTheme=a},_setOption:function(a,b){switch(a){case"handler":this.enableHandler(b);break;case"handlerTheme":this._setHandlerTheme(b);break;default:d.call(this,a,b)}},_handlerTimer:0}),a(b).delegate(":jqmData(scroll)","scrollviewcreate",function(){var b=a(this);if(b.attr("data-"+a.mobile.ns+"scroll")==="none"||b.attr("data-"+a.mobile.ns+"handler")!=="true")return;b.scrollview("enableHandler","true")})}(jQuery,document),function(a,b,c,d){a.widget("tizen.tokentextarea",a.mobile.widget,{_focusStatus:null,_items:null,_viewWidth:0,_reservedWidth:0,_currentWidth:0,_fontSize:0,_anchorWidth:0,_labelWidth:0,_marginWidth:0,options:{label:"To : ",link:null,description:"+ {0}"},_create:function(){var b=this,d=this.element,e=d.jqmData("role"),f=this.options,g="ui-tokentextarea-link",h=a(c.createElement("input")),i=a(c.createElement("span")),j=a(c.createElement("a"));d.hide().empty().addClass("ui-"+e),a(i).text(f.label).addClass("ui-tokentextarea-label").attr("tabindex",0),d.append(i),a(h).addClass("ui-tokentextarea-input ui-tokentextarea-input-visible ui-input-text ui-body-s").attr("role","textbox"),d.append(h);if(f.link===null||a.trim(f.link).length<1||a(f.link).length===0)g+="-dim";a(j).attr("data-role","button").buttonMarkup({inline:!0,icon:"plus",style:"circle"}).attr({href:a.trim(f.link),tabindex:0}).addClass("ui-tokentextarea-link-base").addClass(g).find("span.ui-btn-text").text("Add recipient"),d.append(j),this._bindEvents(),b._focusStatus="init",d.show(),b._viewWidth=d.innerWidth(),b._reservedWidth+=b._calcBlockWidth(j),b._reservedWidth+=b._calcBlockWidth(i),b._fontSize=parseInt(a(j).css("font-size"),10),b._currentWidth=b._reservedWidth,b._modifyInputBoxWidth()},_bindEvents:function(){var b=this,d=b.element,e=b.options,f=d.find(".ui-tokentextarea-input"),g=d.find(".ui-tokentextarea-link-base");d.delegate("div","click",function(c){a(this).hasClass("ui-tokentextarea-sblock")&&b._removeTextBlock();var e=d.find("div.ui-tokentextarea-sblock");typeof e!="undefined"&&e.removeClass("ui-tokentextarea-sblock").addClass("ui-tokentextarea-block"),a(this).removeClass("ui-tokentextarea-block").addClass("ui-tokentextarea-sblock"),d.trigger("select")}),f.bind("keyup",function(c){var d=c.keyCode,e=a(f).val(),g=[],h,i=!1;if(d===8)e.length===0&&b._validateTargetBlock();else if(d===13||d===186||d===188){if(e.length!==0){g=e.split(/[,;]/);for(h=0;h<g.length;h++)g[h].length!==0&&g[h].replace(/\s/g,"").length!==0&&b._addTextBlock(g[h])}f.val(""),i=!0}else b._unlockTextBlock();return!i}),g.click(function(){if(a(g).hasClass("ui-tokentextarea-link-dim"))return;a(f).removeClass("ui-tokentextarea-input-visible").addClass("ui-tokentextarea-input-invisible"),a.mobile.changePage(e.link,{transition:"slide",reverse:!1,changeHash:!1})}),a(c).bind("pagechange.mbe",function(c){if(d.innerWidth()===0)return;b.refresh(),a(f).removeClass("ui-tokentextarea-input-invisible").addClass("ui-tokentextarea-input-visible")}),d.bind("click",function(a){b._focusStatus==="focusOut"&&b.focusIn()})},_addTextBlock:function(b,d){if(arguments.length===0)return;if(!b)return;var e=this,f=e.element,g=b,h=d,i=null,j=null;e._viewWidth===0&&(e._viewWidth=f.innerWidth()),j=a(c.createElement("div")),j.text(g).addClass("ui-tokentextarea-block").attr({"aria-label":"double tap to edit",tabindex:0}),j.css({visibility:"hidden"}),i=f.find("div"),h!==null&&h<=i.length?a(i[h]).before(j):f.find(".ui-tokentextarea-input").before(j),j=e._ellipsisTextBlock(j),j.css({visibility:"visible"}),e._modifyInputBoxWidth(),j.hide(),j.fadeIn("fast",function(){e._currentWidth+=e._calcBlockWidth(j),f.trigger("add")})},_removeTextBlock:function(){var a=this,b=this.element,c=b.find("div.ui-tokentextarea-sblock"),d=null,e=function(){};c!==null&&c.length>0?(a._currentWidth-=a._calcBlockWidth(c),c.fadeOut("fast",function(){c.remove(),a._modifyInputBoxWidth()}),this._eventRemoveCall=!0,b[0].remove&&(d=b[0].remove,b[0].remove=e),b.triggerHandler("remove"),d&&(b[0].remove=d),this._eventRemoveCall=!1):b.find("div:last").removeClass("ui-tokentextarea-block").addClass("ui-tokentextarea-sblock")},_calcBlockWidth:function(b){return a(b).outerWidth(!0)},_unlockTextBlock:function(){var a=this.element,b=a.find("div.ui-tokentextarea-sblock");b&&b.removeClass("ui-tokentextarea-sblock").addClass("ui-tokentextarea-block")},_validateTargetBlock:function(){var a=this,b=a.element,c=b.find("div:last"),d=null;c.hasClass("ui-tokentextarea-sblock")?a._removeTextBlock():(d=b.find("div.ui-tokentextarea-sblock"),d.removeClass("ui-tokentextarea-sblock").addClass("ui-tokentextarea-block"),c.removeClass("ui-tokentextarea-block").addClass("ui-tokentextarea-sblock"))},_ellipsisTextBlock:function(b){var c=this,d=c.element,e=c._viewWidth/2;return c._calcBlockWidth(b)>e&&a(b).width(e-c._marginWidth),b},_modifyInputBoxWidth:function(){var b=this,c=b.element,d=0,e=0,f=0,g=0,h=c.find("div"),i=0,j=0,k=10,l=c.find(".ui-tokentextarea-input");if(c.width()===0)return;b._labelWidth===0&&(b._labelWidth=c.find(".ui-tokentextarea-label").outerWidth(!0),b._anchorWidth=c.find(".ui-tokentextarea-link-base").outerWidth(!0),b._marginWidth=parseInt(a(l).css("margin-left"),10),b._marginWidth+=parseInt(a(l).css("margin-right"),10),b._viewWidth=c.innerWidth()),d=b._marginWidth,e=b._labelWidth,f=b._anchorWidth,g=b._viewWidth-e;for(j=0;j<h.length;j+=1)i=b._calcBlockWidth(h[j]),i>=g+f?i>=g?g=b._viewWidth-i:g=b._viewWidth:i>g?g=b._viewWidth-i:g-=i;g-=d,g<f*2&&(g=b._viewWidth-d),a(l).width(g-f-k)},_stringFormat:function(a){var b=null,c=a,d=0;for(d=1;d<arguments.length;d+=1)b="{"+(d-1)+"}",c=c.replace(b,arguments[d]);return c},_resizeBlocks:function(){var b=this,c=b.element,d=c.find("div"),e=0;for(e=0;e<d.length;e+=1)a(d[e]).css("width","auto"),d[e]=b._ellipsisTextBlock(d[e])},focusIn:function(){if(this._focusStatus==="focusIn")return;var a=this.element;a.find(".ui-tokentextarea-label").attr("tabindex",0).show(),a.find(".ui-tokentextarea-desclabel").remove(),a.find("div.ui-tokentextarea-sblock").removeClass("ui-tokentextarea-sblock").addClass("ui-tokentextarea-block"),a.find("div").attr({"aria-label":"double tap to edit",tabindex:0}).show(),a.find(".ui-tokentextarea-input").removeClass("ui-tokentextarea-input-invisible").addClass("ui-tokentextarea-input-visible").attr("tabindex",0),a.find("a").attr("tabindex",0).show(),this._modifyInputBoxWidth(),this._focusStatus="focusIn",a.removeClass("ui-tokentextarea-focusout").addClass("ui-tokentextarea-focusin").removeAttr("tabindex"),a.find(".ui-tokentextarea-input").focus()},focusOut:function(){if(this._focusStatus==="focusOut")return;var b=this,d=b.element,e=null,f=null,g=null,h="",i=0,j=10,k=d.find(".ui-tokentextarea-label"),l=d.find("span"),m=d.find("div"),n=d.outerWidth(!0)-l.outerWidth(!0)-k.outerWidth(!0),o=0;k.removeAttr("tabindex"),d.find(".ui-tokentextarea-input").removeClass("ui-tokentextarea-input-visible").addClass("ui-tokentextarea-input-invisible").removeAttr("tabindex"),d.find("a").removeAttr("tabindex").hide(),m.removeAttr("aria-label").removeAttr("tabindex").hide(),n-=b._reservedWidth;for(i=0;i<m.length;i++){o=a(m[i]).outerWidth(!0);if(n-o<=0){j=i-1;break}a(m[i]).show(),n-=o}j!==m.length&&(h=b._stringFormat(b.options.description,m.length-j-1),e=a(c.createElement("span")),e.addClass("ui-tokentextarea-desclabel").attr({"aria-label":"more, double tap to edit",tabindex:"-1"}),f=a(c.createElement("span")).text(h).attr("aria-hidden","true"),g=a(c.createElement("span")).text(m.length-j-1).attr("aria-label","and").css("visibility","hidden"),e.append(f),e.append(g),a(m[j]).after(e)),this._focusStatus="focusOut",d.removeClass("ui-tokentextarea-focusin").addClass("ui-tokentextarea-focusout").attr("tabindex",0)},inputText:function(a){var b=this.element;return arguments.length===0?b.find(".ui-tokentextarea-input").val():(b.find(".ui-tokentextarea-input").val(a),a)},select:function(b){var c=this.element,d=null,e=null;if(this._focusStatus==="focusOut")return;return arguments.length===0?(d=c.find("div.ui-tokentextarea-sblock"),d?d.text():null):(this._unlockTextBlock(),e=c.find("div"),e.length>b&&(a(e[b]).removeClass("ui-tokentextarea-block").addClass("ui-tokentextarea-sblock"),c.trigger("select")),null)},add:function(a,b){if(this._focusStatus==="focusOut")return;this._addTextBlock(a,b)},remove:function(b){var c=this,d=this.element,e=d.find("div"),f=0,g=null,h=function(){};if(this._focusStatus==="focusOut")return;arguments.length===0?e.fadeOut("fast",function(){e.remove(),c._modifyInputBoxWidth(),c._trigger("clear")}):isNaN(b)||(f=b<e.length?b:e.length-1,a(e[f]).fadeOut("fast",function(){a(e[f]).remove(),c._modifyInputBoxWidth()}),this._eventRemoveCall=!0,d[0].remove&&(g=d[0].remove,d[0].remove=h),d.triggerHandler("remove"),g&&(d[0].remove=g),this._eventRemoveCall=!1)},length:function(){return this.element.find("div").length},refresh:function(){var a=this,b=this.element.innerWidth();b&&a._viewWidth!==b&&(a._viewWidth=b),a._resizeBlocks(),a._modifyInputBoxWidth()},destroy:function(){var a=this.element,b=null,c=function(){};if(this._eventRemoveCall)return;a.find(".ui-tokentextarea-label").remove(),a.find("div").undelegate("click").remove(),a.find("a").remove(),a.find(".ui-tokentextarea-input").unbind("keyup").remove(),this._eventRemoveCall=!0,a[0].remove&&(b=a[0].remove,a[0].remove=c),a.remove(),b&&(a[0].remove=b),this._eventRemoveCall=!1,this._trigger("destroy")}}),a(c).bind("pagecreate create",function(){a(":jqmData(role='tokentextarea')").tokentextarea()}),a(b).bind("resize",function(){a(":jqmData(role='tokentextarea')").tokentextarea("refresh")})}(jQuery,window,document),function(a,b){a.widget("tizen.searchbar",a.mobile.widget,{options:{theme:null,initSelector:"input[type='search'],:jqmData(type='search'), input[type='tizen-search'],:jqmData(type='tizen-search')"},_create:function(){function t(){setTimeout(function(){h.toggleClass("ui-input-clear-hidden",!c.val())},0)}function u(){g.addClass("ui-input-search-default").removeClass("ui-input-search-wide"),i.addClass("ui-btn-cancel-show").removeClass("ui-btn-cancel-hide")}function v(){g.addClass("ui-input-search-wide").removeClass("ui-input-search-default"),i.addClass("ui-btn-cancel-hide").removeClass("ui-btn-cancel-show"),t()}function w(){var b=a(c).jqmData("icon"),d=a("<div data-role='button' data-style='circle'></div>");d.appendTo(g.parent()).buttonMarkup({icon:b,iconpos:"notext",corners:!0,shadow:!0}),d.addClass("ui-btn-search-front-icon")}var c=this.element,d=this.options,e=d.theme||a.mobile.getInheritedTheme(this.element,"c"),f=" ui-body-"+e,g,h,i,j,k,l,m,n,o,p,q,r=!1,s=!1;a("label[for='"+c.attr("id")+"']").addClass("ui-input-text"),typeof c[0].autocorrect!="undefined"&&!a.support.touchOverflow&&(c[0].setAttribute("autocorrect","off"),c[0].setAttribute("autocomplete","off")),g=c.wrap("<div class='ui-input-search ui-shadow-inset ui-corner-all ui-btn-shadow"+f+"'></div>").parent(),a(this.element).data("cancel-btn")===!0&&(r=!0,g.addClass("ui-input-search-default")),a(this.element).data("icon")!=b&&(s=!0,g.addClass("ui-search-bar-icon")),h=a("<a href='#' class='ui-input-clear' title='clear text'>clear text</a>").bind("click",function(a){if(c.attr("disabled")=="disabled")return!1;c.val("").focus().trigger("change"),h.addClass("ui-input-clear-hidden"),a.preventDefault()}).appendTo(g).buttonMarkup({icon:"deleteSearch",iconpos:"notext",corners:!0,shadow:!0}),t(),c.bind("paste cut keyup focus change blur",t),g.wrapAll("<div class='input-search-bar'></div>"),p=a("<div class='ui-image-search'></div>").appendTo(g),s&&w(),r&&(i=a("<div data-role='button' class='ui-input-cancel' title='clear text'>Cancel</div>").bind("click",function(a){if(c.attr("disabled")=="disabled")return!1;a.preventDefault(),a.stopPropagation(),c.val("").blur().trigger("change"),r&&v()}).appendTo(g.parent()).buttonMarkup({iconpos:"cancel",corners:!0,shadow:!0})),c.focus(function(){if(c.attr("disabled")=="disabled")return!1;r&&u(),g.addClass(a.mobile.focusClass)}).blur(function(){g.removeClass(a.mobile.focusClass)}),j=c.jqmData("default-text"),j!=b&&j.length>0&&(k="ui-input-default-text",l=j.replace(/\s/g,""),m=k+"-"+l,n=a("<style>."+m+":after"+"{content:"+"'"+j+"'"+"}"+"</style>"),a("html > head").append(n),o=a("<div></div>"),o.addClass(k),o.addClass(m),o.tap(function(a){c.blur(),c.focus()}),c.parent().append(o),c.focus(function(){c.parent().find("div.ui-input-default-text").addClass("ui-input-default-hidden")}).blur(function(){var a=c.val();a.length>0?c.parent().find("div.ui-input-default-text").addClass("ui-input-default-hidden"):c.parent().find("div.ui-input-default-text").removeClass("ui-input-default-hidden")})),c.attr("placeholder")||c.attr("placeholder","Search")},disable:function(){this.element.attr("disabled",!0),this.element.parent().addClass("ui-disabled"),a(this.element).blur(),this.element.parent().parent().find(".ui-input-cancel").addClass("ui-disabled")},enable:function(){this.element.attr("disabled",!1),this.element.parent().removeClass("ui-disabled"),this.element.parent().parent().find(".ui-input-cancel").removeClass("ui-disabled"),a(this.element).focus()}}),a(document).bind("pagecreate create",function(b){a.tizen.searchbar.prototype.enhanceWithin(b.target)})}(jQuery),function(a,b,c,d){function e(a,b){var c=a%b;return c<0&&(c=b+c),c}function f(b){this.options=a.extend({},b),this.easing="easeOutQuad",this.reset()}function l(){return Date.now()}var g={scrolling:0,done:1},h=0,i=1,j=-1,k=/src\s*=\s*[\"\'][\w\/.]+.[A-z]+[\"\']/;a.extend(f.prototype,{start:function(a,b,c){this.state=b!==0?g.scrolling:g.done,this.pos=a,this.speed=b,this.duration=c,this.fromPos=0,this.toPos=0,this.startTime=l()},reset:function(){this.state=g.done,this.pos=0,this.speed=0,this.duration=0},update:function(){var b=this.state,c,d,e,f;return b==g.done?this.pos:(c=this.duration,d=l()-this.startTime,d=d>c?c:d,e=this.speed*(1-a.easing[this.easing](d/c,d,0,1,c)),f=this.pos+e/2,this.pos=f,d>=c&&(this.state=g.done),this.pos)},done:function(){return this.state==g.done},getPosition:function(){return this.pos}}),jQuery.widget("mobile.virtualgrid",jQuery.mobile.widget,{options:{template:"",direction:"y",rotation:!1},create:function(){this._create.apply(this,arguments)},_create:function(b){a.extend(this,{_$view:null,_$clip:null,_$rows:null,_tracker:null,_viewSize:0,_clipSize:0,_cellSize:d,_currentItemCount:0,_itemCount:1,_inheritedSize:null,_timerInterval:0,_timerID:0,_timerCB:null,_lastMove:null,_itemData:function(a){return null},_numItemData:0,_cacheItemData:function(a,b){},_totalRowCnt:0,_templateText:null,_maxViewSize:0,_modifyViewPos:0,_maxSizeExceptClip:0,_maxSize:0,_direction:!1,_didDrag:!0,_reservedPos:0,_scalableSize:0,_eventPos:0,_nextPos:0,_movePos:0,_lastY:0,_speedY:0,_lastX:0,_speedX:0,_rowsPerView:0,_fragment:null,_filterRatio:.9,_overflowStartPos:0,_overflowDir:0,_overflowMaxDragDist:100});var e=this,f=a(e.element),g=e.options,h=null;if(!b)return;if(!e._loadData(b))return;e._fragment=c.createDocumentFragment(),e._inheritedSize=e._getinheritedSize(e.element),e._direction=g.direction==="x"?!0:!1,e._$clip=f.addClass("ui-scrollview-clip").addClass("ui-virtualgrid-view"),h=a(c.createElement("div")).addClass("ui-scrollview-view"),e._clipSize=e._calculateClipSize(),e._$clip.append(h),e._$view=h,e._$clip.css("overflow","hidden"),e._$view.css("overflow","hidden"),e._scrollView=a.tizen.scrollview.prototype,e._initScrollView(),e._createTracker(),e._makePositioned(e._$clip),e._timerInterval=1e3/e.options.fps,e._timerID=0,e._timerCB=function(){e._handleMomentumScroll()},f.closest(".ui-content").addClass("ui-virtualgrid-content").css("overflow","hidden"),e._addBehaviors(),e._currentItemCount=0,e._createOverflowArea(),e._createScrollBar(),e.refresh()},_loadData:function(a){var b=this;if(!a.itemData||typeof a.itemData!="function")return!1;b._itemData=a.itemData;if(!a.numItemData)return!1;if(typeof a.numItemData=="function")b._numItemData=a.numItemData();else{if(typeof a.numItemData!="number")return!1;b._numItemData=a.numItemData}return b._getObjectNames(b._itemData(0)),!0},_initLayout:function(){var a=this,b=a.options,c,d;for(c=-1;c<a._rowsPerView+1;c+=1)d=a._$rows[e(c,a._$rows.length)],a._$view.append(d);a._setElementTransform(-a._cellSize),a._replaceRow(a._$view[0].firstChild,a._totalRowCnt-1),b.rotation&&a._rowsPerView>=a._totalRowCnt&&a._replaceRow(a._$view[0].lastChild,0),a._setViewSize()},_setViewSize:function(){var a=this,b=0,c=0;a._direction?(c=a._cellSize*(a._rowsPerView+2),c=parseInt(c,10)+1,a._$view.width(c),a._viewSize=a._$view.width()):(a._$view.height(a._cellSize*(a._rowsPerView+2)),a._$clip.height(a._clipSize),a._viewSize=a._$view.height())},_getViewWidth:function(){var a=this;return a._maxSize},_getViewHeight:function(){var a=this;return a._maxSize},refresh:function(){var b=this,c=b.options,d=0,e=0,f=null;f=a("#"+c.template);if(!f)return;b._templateText=b._insertAriaAttrToTmpl(f.text()),d=b._calculateClipWidth(),e=b._calculateClipHeight(),b._$view.width(d).height(e),b._$clip.width(d).height(e),b._clipSize=b._calculateClipSize(),b._calculateColumnSize(),b._initPageProperty(),b._setScrollBarSize()},_initPageProperty:function(){var b=this,c=0,d,e=0,f=0,g=b._direction?"width":"height";e=b._calculateColumnCount(),f=parseInt(b._numItemData/e,10),b._totalRowCnt=b._numItemData%e===0?f:f+1,b._itemCount=e;if(b._cellSize<=0)return;c=b._clipSize/b._cellSize,c=Math.ceil(c),b._rowsPerView=parseInt(c,10),d=a(b._makeRows(c+2)),b._$view.append(d.children()),b._$view.children().css(g,b._cellSize+"px"),b._$rows=b._$view.children().detach(),b._reservedPos=-b._cellSize,b._scalableSize=-b._cellSize,b._initLayout(),b._blockScroll=b._rowsPerView>b._totalRowCnt,b._maxSizeExceptClip=(b._totalRowCnt-b._rowsPerView)*b._cellSize,b._maxSize=b._totalRowCnt*b._cellSize,b._maxViewSize=b._rowsPerView*b._cellSize,b._modifyViewPos=-b._cellSize,b._clipSize<b._maxViewSize&&(b._modifyViewPos=-b._cellSize+(b._clipSize-b._maxViewSize))},_getinheritedSize:function(b){var c=a(b),d,e,f={ELEMENT_NODE:1,TEXT_NODE:3},g={isDefinedWidth:!1,isDefinedHeight:!1,width:0,height:0};while(c[0].nodeType===f.ELEMENT_NODE&&(g.isDefinedWidth===!1||g.isHeightDefined===!1)){d=c[0].style.height,e=c[0].style.width,g.isDefinedHeight===!1&&d!==""&&(g.isDefinedHeight=!0,g.height=parseInt(d,10)),g.isDefinedWidth===!1&&e!==""&&(g.isDefinedWidth=!0,g.width=parseInt(e,10)),c=c.parent();if(c.hasClass("ui-content"))break}return g},_resize:function(){var a=this,b=null,c=0,d=0,e=0,f=0,g=0,h=0,i=0,j=0,k=null,l=0;a._direction?(l=a._calculateClipHeight(),a._$view.height(l),a._$clip.height(l)):(l=a._calculateClipWidth(),a._$view.width(l),a._$clip.width(l)),d=a._calculateColumnCount(),d!=a._itemCount&&(e=parseInt(a._numItemData/d,10),a._totalRowCnt=a._numItemData%d===0?e:e+1,h=a._itemCount,a._itemCount=d,i=a._getClipPosition(),a._$view.hide(),f=a._replaceRows(d,h,a._totalRowCnt,i),a._maxSizeExceptClip=(a._totalRowCnt-a._rowsPerView)*a._cellSize,a._maxSize=a._totalRowCnt*a._cellSize,a._scalableSize+=-f*a._cellSize,a._reservedPos+=-f*a._cellSize,a._setScrollBarSize(),a._setScrollBarPosition(f),a._$view.show()),g=a._calculateClipSize(),g!==a._clipSize&&(c=g/a._cellSize,c=parseInt(Math.ceil(c),10),c>a._rowsPerView?a._increaseRow(c-a._rowsPerView):c<a._rowsPerView&&a._decreaseRow(a._rowsPerView-c),a._$rows=a._$view.children(),a._$rows.sort(function(a,b){return a.getAttribute("row-index")-b.getAttribute("row-index")}),a._rowsPerView=c,a._clipSize=g,a._blockScroll=a._rowsPerView>a._totalRowCnt,a._maxSizeExceptClip=(a._totalRowCnt-a._rowsPerView)*a._cellSize,a._maxSize=a._totalRowCnt*a._cellSize,a._maxViewSize=a._rowsPerView*a._cellSize,a._clipSize<a._maxViewSize&&(a._modifyViewPos=-a._cellSize+(a._clipSize-a._maxViewSize)),a._direction?a._$clip.width(a._clipSize):a._$clip.height(a._clipSize),a._setScrollBarSize(),a._setScrollBarPosition(0),a._setViewSize())},resize:function(){var b=this,c=0,d=a(".ui-virtualgrid-view");b._inheritedSize=b._getinheritedSize(b.element),d.length!==0&&b._resize()},_initScrollView:function(){var b=this,c=b.options.direction;a.extend(b.options,b._scrollView.options),b.options.direction=c,b.options.moveThreshold=10,b.options.showScrollBars=!1,b._getScrollHierarchy=b._scrollView._getScrollHierarchy,b._makePositioned=b._scrollView._makePositioned,b._set_scrollbar_size=b._scrollView._set_scrollbar_size,b._setStyleTransform=b._scrollView._setElementTransform,b._hideOverflowIndicator=b._scrollView._hideOverflowIndicator,b._showOverflowIndicator=b._scrollView._showOverflowIndicator,b._setGestureScroll=b._scrollView._setGestureScroll},_createTracker:function(){var a=this;a._tracker=new f(a.options),a._direction?(a._hTracker=a._tracker,a._$clip.width(a._clipSize)):(a._vTracker=a._tracker,a._$clip.height(a._clipSize))},_createOverflowArea:function(){var b=this,c='<div class="ui-virtualgrid-overflow-indicator-',d='-top"></div>',e='-bottom"></div>';if(b.options.rotation)return;b._direction?(b._overflowTop=a(c+"x"+d),b._overflowBottom=a(c+"x"+e)):(b._overflowTop=a(c+"y"+d),b._overflowBottom=a(c+"y"+e)),b._$clip.append(b._overflowTop),b._$clip.append(b._overflowBottom),b._overflowDisplayed=!1},_hideVGOverflowIndicator:function(){if(this._overflowDisplayed===!1)return;this._overflowTop.animate({opacity:0},300),this._overflowBottom.animate({opacity:0},300),this._overflowDisplayed=!1},_createScrollBar:function(){var a=this,b='<div class="ui-scrollbar ui-scrollbar-',c='"><div class="ui-scrollbar-track"><div class="ui-scrollbar-thumb"></div></div></div>';if(a.options.rotation)return;a._direction?(a._$clip.append(b+"x"+c),a._hScrollBar=a._$clip.children(".ui-scrollbar-x"),a._hScrollBar.find(".ui-scrollbar-thumb").addClass("ui-scrollbar-thumb-x")):(a._$clip.append(b+"y"+c),a._vScrollBar=a._$clip.children(".ui-scrollbar-y"),a._vScrollBar.find(".ui-scrollbar-thumb").addClass("ui-scrollbar-thumb-y"))},_setScrollBarSize:function(){var a=this,b=0,c=0,d,e,f;if(a.options.rotation)return;b=parseInt(a._maxViewSize/a._clipSize,10),a._direction?(d=a._hScrollBar.find(".ui-scrollbar-thumb"),e="width",c=d.width(),f="ui-scrollbar-thumb-x",a._hScrollBar.css("width",a._clipSize)):(d=a._vScrollBar.find(".ui-scrollbar-thumb"),e="height",f="ui-scrollbar-thumb-y",c=d.height(),a._vScrollBar.css("height",a._clipSize)),b>c?(d.removeClass(f),d.css(e,b)):b=c,a._itemScrollSize=parseFloat((a._clipSize-b)/(a._totalRowCnt-a._rowsPerView)),a._itemScrollSize=Math.round(a._itemScrollSize*100)/100},_setScrollBarPosition:function(a,b){var c=this,d=null,e="0px",f="0px",g;if(c.options.rotation)return;c._currentItemCount=c._currentItemCount+a,c._vScrollBar?(d=c._vScrollBar.find(".ui-scrollbar-thumb"),f=c._currentItemCount*c._itemScrollSize+"px"):(d=c._hScrollBar.find(".ui-scrollbar-thumb"),e=c._currentItemCount*c._itemScrollSize+"px"),c._setStyleTransform(d,e,f,b)},_hideScrollBars:function(){var a=this,b="ui-scrollbar-visible";if(a.options.rotation)return;a._vScrollBar?a._vScrollBar.removeClass(b):a._hScrollBar.removeClass(b)},_showScrollBars:function(){var a=this,b="ui-scrollbar-visible";if(a.options.rotation)return;a._vScrollBar?a._vScrollBar.addClass(b):a._hScrollBar.addClass(b)},centerTo:function(b){var c=this,d=null,e=null,f=-1,g=c._$rows.length,h,i;if(!c.options.rotation)return;for(i=0;i<g;++i){d=a(c._$rows[i]),e=d.children("."+b);if(e.length){f=parseInt(d.attr("row-index"),10);break}}if(f===-1){f=c._getTargetRowIndex(b);if(f===-1)return}h=-(f*c._cellSize-(c._clipSize-c._cellSize)/2),c._direction?c.scrollTo(h,0):c.scrollTo(0,h)},_getTargetRowIndex:function(a){var b=this,c=b._numItemData,d=b._itemCount,e=b._direction?"top":"left",f="",g=b._totalRowCnt,h;for(h=0;h<c;++h){f=b._makeHtmlData(h,h%d,e);if(b._hasClassItem(f,a)){g=parseInt(h/d,10);break}}return g===b._totalRowCnt?-1:g},_hasClassItem:function(a,b){var c=this,d=c._getItemClass(a);return d.indexOf(b)===-1?!1:d.indexOf("virtualgrid-item")===-1?!1:!0},_getItemClass:function(a){var b=a.indexOf("class"),c=Math.min(a.indexOf('"',b),a.indexOf("'",b)),d=Math.min(a.indexOf('"',c+1),a.indexOf("'",c+1));return a.slice(c+1,d)},scrollTo:function(a,b,c){var d=this;d._direction?(a-=d._cellSize,d._sx=d._reservedPos,d._reservedPos=a):(b-=d._cellSize,d._sy=d._reservedPos,d._reservedPos=b),d._scrollView.scrollTo.apply(this,[a,b,c])},getScrollPosition:function(){return this.direction?{x:-this._ry,y:0}:{x:0,y:-this._ry}},_setScrollPosition:function(a,b){var c=this,d=c._scalableSize,f=c._direction?a:b,g=f-d,k=parseInt(g/c._cellSize,10),l=0,m=0,n=0,o=c._rowsPerView+2,p=c._$view[0];if(c._blockScroll){g>0&&f>=-c._cellSize&&c._scalableSize>=-c._cellSize&&(c._overflowDir=i),g<0&&c._scalableSize<=-(c._maxSizeExceptClip+c._cellSize)&&(c._overflowDir=j);return}if(!c.options.rotation){if(g>0&&f>=-c._cellSize&&c._scalableSize>=-c._cellSize){c._stopMScroll(),c._scalableSize=-c._cellSize,c._setElementTransform(-c._cellSize),c._overflowDir===h&&(c._overflowDir=i);return}if(g<0&&c._scalableSize<=-(c._maxSizeExceptClip+c._cellSize)){c._stopMScroll(),c._scalableSize=-(c._maxSizeExceptClip+c._cellSize),c._setElementTransform(c._modifyViewPos),c._overflowDir===h&&(c._overflowDir=j);return}}n=Math.abs(k)<o?0:k>0?k-o:k+o;if(k>0)for(l=n;l<k;++l)m=-parseInt(d/c._cellSize+l+3,10),c._replaceRow(p.lastChild,e(m,c._totalRowCnt)),p.insertBefore(p.lastChild,p.firstChild);else if(k<0)for(l=n;l>k;--l)m=c._rowsPerView-parseInt(d/c._cellSize+l,10),c._replaceRow(p.firstChild,e(m,c._totalRowCnt)),p.insertBefore(p.firstChild,p.lastChild.nextSibling);c._setScrollBarPosition(-k),c._scalableSize+=k*c._cellSize,c._setElementTransform(f-c._scalableSize-c._cellSize)},_setElementTransform:function(a){var b=this,c=0,d=0;b._direction?c=a+"px":d=a+"px",b._setStyleTransform(b._$view,c,d)},_handleMomentumScroll:function(){var a=this,b=a.options,c=!1,d=this._$view,e=0,f=0,g=a._tracker;g&&(g.update(),a._direction?e=g.getPosition():f=g.getPosition(),c=!g.done()),a._setScrollPosition(e,f),b.rotation?a._reservedPos=a._direction?e:f:(c=!g.done(),a._reservedPos=a._direction?e:f,a._reservedPos=a._reservedPos<=-(a._maxSizeExceptClip-a._modifyViewPos)?-(a._maxSizeExceptClip+a._cellSize):a._reservedPos,a._reservedPos=a._reservedPos>-a._cellSize?-a._cellSize:a._reservedPos),a._$clip.trigger(a.options.updateEventName,[{x:e,y:f}]),c?a._timerID=setTimeout(a._timerCB,a._timerInterval):a._stopMScroll()},_startMScroll:function(a,b){var c=this;c._direction?c._sx=c._reservedPos:c._sy=c._reservedPos,c._scrollView._startMScroll.apply(c,[a,b])},_stopMScroll:function(){this._scrollView._stopMScroll.apply(this)},_enableTracking:function(){var a=this;a._$view.bind(a._dragMoveEvt,a._dragMoveCB),a._$view.bind(a._dragStopEvt,a._dragStopCB),a._scrollView._enableTracking.apply(a)},_disableTracking:function(){var a=this;a._$view.unbind(a._dragMoveEvt,a._dragMoveCB),a._$view.unbind(a._dragStopEvt,a._dragStopCB),a._scrollView._disableTracking.apply(a)},_handleDragStart:function(a,b,c){var d=this;d._scrollView._handleDragStart.apply(this,[a,b,c]),d._eventPos=d._direction?b:c,d._nextPos=d._reservedPos},_handleDragMove:function(a,b,c){var d=this,e=b-d._lastX,f=c-d._lastY,g=0,j=0,k=0,m=0,n=0,o=0,p=null;return d._lastMove=l(),d._speedX=e,d._speedY=f,d._didDrag=!0,d._lastX=b,d._lastY=c,d._direction?(d._movePos=b-d._eventPos,g=d._nextPos+d._movePos,o=b):(d._movePos=c-d._eventPos,j=d._nextPos+d._movePos,o=c),d._showScrollBars(),d._setScrollPosition(g,j),d._overflowDir!==
-h&&(p=d._overflowDir===i?d._overflowTop:d._overflowBottom,d._overflowDisplayed||(d._overflowDisplayed=!0,d._overflowStartPos=o),k=(o-d._overflowStartPos)*d._overflowDir,n=k<0?0:k>d._overflowMaxDragDist?1:k/d._overflowMaxDragDist,p.css("opacity",n)),!1},_handleDragStop:function(a){var b=this;return b._reservedPos=b._movePos?b._nextPos+b._movePos:b._reservedPos,b._scrollView._handleDragStop.apply(this,[a]),b._overflowDir!==h&&(b._overflowDir=h,b._hideVGOverflowIndicator()),b._didDrag?!1:d},_addBehaviors:function(){var d=this;d.options.eventType==="mouse"?(d._dragStartEvt="mousedown",d._dragStartCB=function(a){return d._handleDragStart(a,a.clientX,a.clientY)},d._dragMoveEvt="mousemove",d._dragMoveCB=function(a){return d._handleDragMove(a,a.clientX,a.clientY)},d._dragStopEvt="mouseup",d._dragStopCB=function(a){return d._handleDragStop(a,a.clientX,a.clientY)},d._$view.bind("vclick",function(a){return!d._didDrag})):(d._dragStartEvt="touchstart",d._dragStartCB=function(a){var b=a.originalEvent.targetTouches[0];return d._handleDragStart(a,b.pageX,b.pageY)},d._dragMoveEvt="touchmove",d._dragMoveCB=function(a){var b=a.originalEvent.targetTouches[0];return d._handleDragMove(a,b.pageX,b.pageY)},d._dragStopEvt="touchend",d._dragStopCB=function(a){return d._handleDragStop(a)}),d._$view.bind(d._dragStartEvt,d._dragStartCB),d._$view.delegate(".virtualgrid-item","click",function(b){var c=a(this);c.trigger("select",this)}),a(b).bind("resize",function(b){var c=0,e=a(".ui-virtualgrid-view");e.length!==0&&d._resize()}),a(c).one("pageshow",function(c){var e=a(d.element).parents(".ui-page"),f=e.find(":jqmData(role='header')"),g=e.find(":jqmData(role='footer')"),h=e.find(":jqmData(role='content')"),i=g?g.height():0,j=f?f.height():0;e&&h&&(h.height(b.innerHeight-j-i).css("overflow","hidden"),h.addClass("ui-virtualgrid-content"))})},_calculateClipSize:function(){var a=this,b=0;return a._direction?b=a._calculateClipWidth():b=a._calculateClipHeight(),b},_calculateClipWidth:function(){var c=this,d=c._$clip.parent(),e=0,f=a(b).width();return c._inheritedSize.isDefinedWidth?c._inheritedSize.width:(d.hasClass("ui-content")?(e=parseInt(d.css("padding-left"),10),f-=e||0,e=parseInt(d.css("padding-right"),10),f-=e||0):f=c._$clip.width(),f)},_calculateClipHeight:function(){var c=this,d=c._$clip.parent(),e=null,f=null,g=0,h=a(b).height();return c._inheritedSize.isDefinedHeight?c._inheritedSize.height:(d.hasClass("ui-content")?(g=parseInt(d.css("padding-top"),10),h-=g||0,g=parseInt(d.css("padding-bottom"),10),h-=g||0,e=d.siblings(".ui-header"),f=d.siblings(".ui-footer"),e&&(e.outerHeight(!0)===null?h-=a(".ui-header").outerHeight()||0:h-=e.outerHeight(!0)),f&&(h-=f.outerHeight(!0))):h=c._$clip.height(),h)},_calculateColumnSize:function(){var b=this,c,d;c=a(b._makeRows(1)),b._$view.append(c.children().first()),b._direction?(b._viewSize=b._$view.width(),d=b._$view.children().first().children().first(),b._cellSize=d.outerWidth(!0),b._cellOtherSize=d.outerHeight(!0)):(b._viewSize=b._$view.height(),d=b._$view.children().first().children().first(),b._cellSize=d.outerHeight(!0),b._cellOtherSize=d.outerWidth(!0)),c.remove(),b._$view.children().remove()},_calculateColumnCount:function(){var a=this,b=a._$clip,c=a._direction?b.innerHeight():b.innerWidth(),d=0;return a._direction?c-=parseInt(b.css("padding-top"),10)+parseInt(b.css("padding-bottom"),10):c-=parseInt(b.css("padding-left"),10)+parseInt(b.css("padding-right"),10),d=parseInt(c/a._cellOtherSize,10),d>0?d:1},_getClipPosition:function(){var a=this,b=null,c=null,d=-a._cellSize,e=a._$view.closest(".ui-scrollview-view");return e&&(b=e.css("-webkit-transform"),c=b.substr(7),c=c.substr(0,c.length-1),c=c.split(", "),d=Math.abs(c[5])),d},_makeRows:function(a){var b=this,c=0,d=null,e=null;e=b._createElement("div"),e.setAttribute("class","ui-scrollview-view");for(c=0;c<a;c+=1)d=b._makeRow(c),b._direction&&(d.style.top=0,d.style.left=c*b._cellSize),e.appendChild(d);return e},_makeRow:function(a){var b=this,c=a*b._itemCount,d=0,e=b._direction?"ui-virtualgrid-wrapblock-x":"ui-virtualgrid-wrapblock-y",f=b._createElement("div"),g="",h=b._direction?"top":"left";for(d=0;d<b._itemCount;d++)g+=b._makeHtmlData(c,d,h),c+=1;return f.innerHTML=g,f.setAttribute("class",e),f.setAttribute("row-index",String(a)),b._fragment.appendChild(f),f},_makeHtmlData:function(a,b,c){var d=this,e="",f=null;return f=d._itemData(a),f&&(e=d._getConvertedTmplStr(f),e=d._insertPosToTmplStr(e,c,b*d._cellOtherSize)),e},_insertPosToTmplStr:function(a,b,c){var d=a.indexOf(">"),e=-1,f,g,h,i=!1,j=0,k,l=0;if(d===-1)return;f=a.slice(0,d),g=a.slice(d,a.length),e=f.indexOf("class");if(e!==-1){k=f.length;for(l=e+6;l<k;l++)if(f.charAt(l)==='"'||f.charAt(l)==="'"){if(i!==!1){j=l;break}i=!0}h=f.slice(0,j)+" virtualgrid-item"+f.slice(j,k)+g}else h=f+' class="virtualgrid-item"'+g;return isNaN(c)||(h=h.replace(">",' style="'+b+": "+String(c)+'px">')),h},_increaseRow:function(b){var c=this,d=c.options.rotation,f=c._totalRowCnt,g=c._$view[0],h=null,i=g.lastChild,j=null,k=0,l=0,m;if(!i)return;l=parseInt(i.getAttribute("row-index"),10),d||(h=g.firstChild,k=parseInt(h.getAttribute("row-index"),10));for(m=0;m<b;++m){if(l>=f-1&&!d){if(k==0)break;j=c._makeRow(--k),g.insertBefore(j,h),h=j}else j=c._makeRow(e(++l,f)),g.appendChild(j);c._direction?a(j).width(c._cellSize):a(j).height(c._cellSize)}},_decreaseRow:function(a){var b=this,c=b._$view[0],d;for(d=0;d<a;++d)c.removeChild(c.lastChild)},_replaceRows:function(b,c,d,f){var g=this,h=g._$view.children(),i=0,j=0,k=0,l=1,m=g._filterRatio*g._cellSize+g._cellSize,n=0;m<f&&(l+=1),i=parseInt(a(h[l]).attr("row-index"),10),i===0?j=d-l:(j=Math.round(i*c/b),j+g._rowsPerView>=d&&(j=d-g._rowsPerView),k=i-j,j-=l);for(n=0;n<h.length;n+=1)g._replaceRow(h[n],e(j,g._totalRowCnt)),j++;return-k},_replaceRow:function(a,b){var c=this,d=null;while(a.hasChildNodes())a.removeChild(a.lastChild);d=c._makeRow(b);while(d.children.length)a.appendChild(d.children[0]);a.setAttribute("row-index",d.getAttribute("row-index")),d.parentNode.removeChild(d)},_createElement:function(a){var b=c.createElement(a);return this._fragment.appendChild(b),b},_getObjectNames:function(a){var b=[],c="";for(c in a)b.push(c);this._properties=b},_getConvertedTmplStr:function(a){var b=this,c=b._properties,d=0,e,f="";if(!a)return;e=b._templateText;for(d=0;d<c.length;d++)e=b._strReplace(e,"${"+c[d]+"}",a[c[d]]);return e=b._changeImgSrcAriaAttrFromTmpl(e),e},_changeImgSrcAriaAttrFromTmpl:function(a){var b=this,c="",d,e="",f="",g,h,i,j;i=a,d=i.indexOf("$ARIA-IMG-SRC-ALT$");while(d!==-1)g="",e+=i.slice(0,d+19),f=i.slice(d+19,i.length),j=f.match(k),j&&(h=j[0].lastIndexOf("/"),h!==-1&&(g=j[0].slice(h+1,-1))),e=e.replace("$ARIA-IMG-SRC-ALT$",g),i=f,d=i.indexOf("$ARIA-IMG-SRC-ALT$"),c=e+f;return c===""&&(c=a),c},_insertAriaAttrToTmpl:function(a){var b="",c,d="",e="",f;f=a.replace("<div",'<div tabindex="0" aria-selected="true"'),c=f.indexOf("<img");if(c!==-1){while(c!==-1)d+=f.slice(0,c+4),e=f.slice(c+4,f.length),d+=' role="img" alt="$ARIA-IMG-SRC-ALT$"',f=e,c=f.indexOf("<img"),b=d+e;f=b,c=f.indexOf("<span"),d="";while(c!==-1)d+=f.slice(0,c+5),e=f.slice(c+5,f.length),d+=' aria-hidden="true" tabindex="-1"',f=e,c=f.indexOf("<span"),b=d+e}return b===""&&(b=a),b},_strReplace:function(a,b,c){var d=a,e=a.indexOf(b);while(e!==-1)d=d.replace(b,c),e=d.indexOf(b);return d}}),a(c).bind("pagecreate create",function(b){a(":jqmData(role='virtualgrid')").virtualgrid()})}(jQuery,window,document),function(a,b){ensureNS("jQuery.mobile.tizen"),jQuery.extend(jQuery.mobile.tizen,{_widgetPrototypes:{},loadPrototype:function(c,d){function h(a){return a.replace(/\$\{FRAMEWORK_ROOT\}/g,g)}function i(a,b){var c;for(var d in a)typeof a[d]=="string"?(c=a[d],a[d]=b.find(a[d]),c.substring(0,1)==="#"&&a[d].removeAttr("id")):typeof a[d]=="object"&&(a[d]=i(a[d],b));return a}var e=b,f=a("script[data-framework-version][data-framework-root][data-framework-theme]"),g=f.attr("data-framework-root")+"/"+f.attr("data-framework-version")+"/";if(typeof c=="string"){e=a.mobile.tizen._widgetPrototypes[c];if(e===b){var j=g+"proto-html"+"/"+f.attr("data-framework-theme");a.ajax({url:j+"/"+c+".prototype.html",async:!1,dataType:"html"}).success(function(b,d,f){a.mobile.tizen._widgetPrototypes[c]=a("<div>").html(h(b)),e=a.mobile.tizen._widgetPrototypes[c].clone()})}}else c.key!==b&&(e=a.mobile.tizen._widgetPrototypes[c.key]),e===b?c.proto!==b&&(e=a("<div>").html(h(c.proto)),c.key!==b&&(a.mobile.tizen._widgetPrototypes[c.key]=e.clone())):e=e.clone();return e!=b&&d!=b&&(e=i(d,e)),e}})}(jQuery),function(a,b,c){a.widget("tizen.progress",a.mobile.widget,{options:{style:"circle",running:!1},show:function(){a(this.element).show()},hide:function(){a(this.element).hide()},_start:function(){this.init||(a(this.element).append(this.html),this.init=!0),this.show(),a(this.element).find(".ui-progress-"+this.options.style).addClass(this.runningClass)},_stop:function(){a(this.element).find(".ui-progress-"+this.options.style).removeClass(this.runningClass)},running:function(a){if(a===c)return this.options.running;this._setOption("running",a)},_setOption:function(a,c){if(a==="running"){if(typeof c!="boolean"){b.alert("running value MUST be boolean type!");return}this.options.running=c,this._refresh()}},_refresh:function(){this.options.running?this._start():this._stop()},_create:function(){var b=this,c=this.element,d=c.jqmData("style"),e,f;d?this.options.style=d:d=this.options.style,d=="circle"?(a(this.element).addClass("ui-progress-container-circle"),e='<div class="ui-progress-circle"></div>'):d==="pending"&&(a(this.element).addClass("ui-progressbar"),e='<div class="ui-progressbar-bg"><div class="ui-progress-pending"></div></div>'),this.html=a(e),f="ui-progress-"+d+"-running",a.extend(this,{init:!1,runningClass:f}),d==="pending"&&(a(this.element).append(this.html),this.init=!0),this._refresh()}}),a(document).bind("pagecreate create",function(b){a(b.target).find(":jqmData(role='progress')").progress()})}(jQuery,this),function(a,b){function c(){var b=a("script[data-framework-version][data-framework-root][data-framework-theme]");return b.attr("data-framework-root")+"/"+b.attr("data-framework-version")+"/themes/"+b.attr("data-framework-theme")+"/proto-html"}a.widget("tizen.widgetex",a.mobile.widget,{_createWidget:function(){a.tizen.widgetex.loadPrototype.call(this,this.namespace+"."+this.widgetName),a.mobile.widget.prototype._createWidget.apply(this,arguments)},_init:function(){if(this.element===b)return;var c=this.element.closest(".ui-page"),d=this,e={};c.is(":visible")?this._realize():c.bind("pageshow",function(){d._realize()}),a.extend(e,this.options),this.options={},this._setOptions(e)},_getCreateOptions:function(){if(this.element.is("input")&&this._value!==b){var c=this.element.attr("type")==="checkbox"||this.element.attr("type")==="radio"?this.element.is(":checked"):this.element.is("[value]")?this.element.attr("value"):b;c!=b&&this.element.attr(this._value.attr,c)}return a.mobile.widget.prototype._getCreateOptions.apply(this,arguments)},_setOption:function(c,d){var e="_set"+c.replace(/^[a-z]/,function(a){return a.toUpperCase()});this[e]!==b?this[e](d):a.mobile.widget.prototype._setOption.apply(this,arguments)},_setDisabled:function(b){a.Widget.prototype._setOption.call(this,"disabled",b),this.element.is("input")&&this.element.attr("disabled",b)},_setValue:function(b){a.tizen.widgetex.setValue(this,b)},_realize:function(){}}),a.tizen.widgetex.setValue=function(a,c){if(a._value!==b){var d=a._value.makeString?a._value.makeString(c):c,e;a.element.attr(a._value.attr,d),a._value.signal!==b&&a.element.triggerHandler(a._value.signal,c),a.element.is("input")&&(e=a.element.attr("type"),e==="checkbox"||e==="radio"?c?a.element.attr("checked",!0):a.element.removeAttr("checked"):a.element.attr("value",d),a.element.trigger("change"))}},a.tizen.widgetex.assignElements=function(b,c){var d={},e;for(e in c)typeof c[e]=="string"?(d[e]=b.find(c[e]),c[e].match(/^#/)&&d[e].removeAttr("id")):typeof c[e]=="object"&&(d[e]=a.tizen.widgetex.assignElements(b,c[e]));return d},a.tizen.widgetex.loadPrototype=function(d,e){var f=d.split("."),g,h,i,j=!1,k,l;f.length==2&&(g=f[0],h=f[1],a[g][h].prototype._htmlProto!==b&&(i=a[g][h].prototype._htmlProto.source,i===b&&(i=h,j=!0),typeof i=="string"?j?(d=i,l=c(),a.ajax({url:l+"/"+d+".prototype.html",async:!1,dataType:"html"}).success(function(b,c,d){i=a("<div></div>").html(b).jqmData("tizen.widgetex.ajax.fail",!1)}),i=a("<div></div>").text("Failed to load proto for widget "+g+"."+h+"!").css({background:"red",color:"blue",border:"1px solid black"}).jqmData("tizen.widgetex.ajax.fail",!0)):i=a(i).jqmData("tizen.widgetex.ajax.fail",!1):i.jqmData("tizen.widgetex.ajax.fail",!1),k=i,a[g][h].prototype._htmlProto.source=i,a[g][h].prototype._htmlProto.ui!==b&&a.extend(this,{_ui:a.tizen.widgetex.assignElements(k.clone(),a[g][h].prototype._htmlProto.ui)})))}}(jQuery),function(a,b,c){a.widget("tizen.progressbar",a.mobile.widget,{options:{value:0,max:100},min:0,_create:function(){this.element.addClass("ui-progressbar").attr({role:"progressbar","aria-valuemin":this.min,"aria-valuemax":this.options.max,"aria-valuenow":this._value()}),this.valueDiv=a("<div class='ui-progressbar-value'></div>").appendTo(this.element),this.valueDiv.wrap("<div class='ui-progressbar-bg'></div>"),this.oldValue=this._value(),this._refreshValue()},_destroy:function(){this.element.removeClass("ui-progressbar").removeAttr("role").removeAttr("aria-valuemin").removeAttr("aria-valuemax").removeAttr("aria-valuenow"),this.valueDiv.remove()},value:function(a){return a===c?this._value():(this._setOption("value",a),this)},_setOption:function(a,b){a==="value"&&(this.options.value=b,this._refreshValue(),this._value()===this.options.max&&this.element.trigger("complete"))},_value:function(){var a=this.options.value;return typeof a!="number"&&(a=0),Math.min(this.options.max,Math.max(this.min,a))},_percentage:function(){return 100*this._value()/this.options.max},_refreshValue:function(){var a=this.value(),b=this._percentage();this.oldValue!==a&&(this.oldValue=a,this.element.trigger("change")),this.valueDiv.toggle(a>this.min).width(b.toFixed(0)+"%"),this.element.attr("aria-valuenow",a)}}),a(document).bind("pagecreate",function(b){a(b.target).find(":jqmData(role='progressbar')").progressbar()})}(jQuery,this),function(a){a.widget("tizen.swipe",a.mobile.widget,{options:{theme:null},_create:function(){var a=this.element.jqmData("theme")||this.options.theme||this.element.parent().jqmData("theme")||"s";this.options.theme=a,this._isopen=!1,this.refresh()},refresh:function(){this._cleanupDom();var b=this,c,d,e,f,g;c="ui-body-"+this.options.theme,this.element.parent().hasClass("ui-listview")||this.element.parent().listview(),this.element.addClass("ui-swipe"),d=this.element.find(':jqmData(role="swipe-item-cover")'),f=this.element.find(':jqmData(role="swipe-item")'),this._covers=d,this._item=f,f.addClass("ui-swipe-item"),e=c,g=f.parent().attr("class").match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/),d.each(function(){var c=a(this);g&&(e=g[0]),c.addClass("ui-swipe-item-cover"),c.addClass(e),c.has(".ui-swipe-item-cover-inner").length===0&&c.wrapInner(a("<span/>").addClass("ui-swipe-item-cover-inner"));if(!c.data("animateRight")||!c.data("animateLeft"))c.data("animateRight",function(){b._animateCover(c,110,f)}),c.data("animateLeft",function(){b._animateCover(c,0,f)});f.bind("swipeleft",c.data("animateLeft")),c.bind("swiperight",c.data("animateRight")),f.find(".ui-btn").bind("vclick",c.data("animateLeft"))})},_cleanupDom:function(){var a=this,b,c,d=b,e,f,g,h,i;b="ui-body-"+this.options.theme,this.element.removeClass("ui-swipe"),c=this.element.find(':jqmData(role="swipe-item-cover")'),e=this.element.find(':jqmData(role="swipe-item")'),e.removeClass("ui-swipe-item"),c.removeClass("ui-swipe-item-cover"),f=e.attr("class"),g=f&&f.match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/),g&&(d=g[0]),c.removeClass(d),i=c.find(".ui-swipe-item-cover-inner"),i.children().unwrap(),h=i.text(),h&&(c.append(h),i.remove()),c.data("animateRight")&&c.data("animateLeft")&&(c.unbind("swiperight",c.data("animateRight")),e.unbind("swipeleft",c.data("animateLeft")),e.find(".ui-btn").unbind("vclick",c.data("animateLeft")),c.data("animateRight",null),c.data("animateLeft",null))},_animateCover:function(b,c,d){var e=this,f={easing:"linear",duration:"normal",queue:!0,complete:function(){b.trigger("animationend")}};a(this.element.parent()).find(":jqmData(role='swipe')").each(function(){this!==e.element.get(0)&&a(this).swipe("opened")&&a(this).swipe("close")}),c==110?this._isopen=!0:this._isopen=!1,b.stop(),b.clearQueue(),b.trigger("animationstart"),b.animate({left:c+"%"},f),c==0?d.animate({opacity:0},"slow"):d.animate({opacity:1},"slow")},destroy:function(){this._cleanupDom()},open:function(){var b=this;a(b._covers).each(function(){var c=a(this);b._animateCover(c,110,b._item)})},opened:function(){return this._isopen},close:function(){var b=this;a(b._covers).each(function(){var c=a(this);b._animateCover(c,0,b._item)})}}),a(document).bind("pagecreate",function(b){a(b.target).find(":jqmData(role='swipe')").swipe()})}(jQuery),function(a,b){a.widget("tizen.tabbar",a.mobile.widget,{options:{iconpos:"top",grid:null,defaultList:4,initSelector:":jqmData(role='tabbar')"},_create:function(){var c=this.element,d,e,f,g=a.mobile.listview.prototype.options.theme,h=window.innerWidth||a(window).width(),i=window.innerHeight||a(window).height(),j="<div class='ui-tabbar-divider ui-tabbar-divider-left'></div>",k="<div class='ui-tabbar-divider ui-tabbar-divider-right'></div>",l;l=h>i&&h-i,l?c.removeClass("ui-portrait-tabbar").addClass("ui-landscape-tabbar"):c.removeClass("ui-landscape-tabbar").addClass("ui-portrait-tabbar"),c.find("a").length&&(d=c.find("a"),f=d.filter(":jqmData(icon)").length?this.options.iconpos:b,e=d.html().length?!0:!1),c.parents(".ui-header").length&&c.parents(".ui-scrollview-view").length?(c.find("li").addClass("tabbar-scroll-li"),c.find("ul").addClass("tabbar-scroll-ul"),a(j).appendTo(c.parents(".ui-scrollview-clip")),a(k).appendTo(c.parents(".ui-scrollview-clip")),a(".ui-tabbar-divider-left").hide(),a(".ui-tabbar-divider-right").hide(),c.parents(".ui-scrollview-view").data("default-list")&&(this.options.defaultList=c.parents(".ui-scrollview-view").data("default-list")),c.find("li").css("width",window.innerWidth/this.options.defaultList+"px")):c.find("ul").children().length&&c.addClass("ui-navbar").find("ul").grid({grid:this.options.grid}),c.parents(".ui-footer").length&&c.find("li").addClass("ui-tab-btn-style"),c.siblings(".ui-title").length&&c.parents(".ui-header").addClass("ui-title-tabbar"),f||c.addClass("ui-tabbar-noicons"),e||c.addClass("ui-tabbar-notext"),e&&f&&c.parents(".ui-header").addClass("ui-title-tabbar-multiline"),c.find("a").length&&d.buttonMarkup({corners:!1,shadow:!1,iconpos:f}),c.find(".ui-state-persist").length&&c.addClass("ui-tabbar-persist"),c.delegate("a","vclick",function(b){d.not(".ui-state-persist").removeClass(a.mobile.activeBtnClass),a(this).addClass(a.mobile.activeBtnClass)}),c.addClass("ui-tabbar"),a(document).bind("pagebeforeshow",function(b,c){var d=a(b.target).find(":jqmData(role='footer')"),e=d.find(":jqmData(role='tabbar')"),f=e.siblings(":jqmData(icon='naviframe-more')"),g=e.siblings(".ui-btn-back");d.css("position","fixed").css("bottom",0).css("height",e.height()),f.length&&e.addClass("ui-tabbar-margin-more"),g.length&&e.addClass("ui-tabbar-margin-back")}),c.bind("touchstart vmousedown",function(b){var c=a(b.target).parents(".ui-scrollview-view");c.offset()&&(c.offset().left<0?a(".ui-tabbar-divider-left").show():a(".ui-tabbar-divider-left").hide(),c.width()-c.parents(".ui-scrollview-clip").width()==Math.abs(c.offset().left)?a(".ui-tabbar-divider-right").hide():a(".ui-tabbar-divider-right").show())}),this._bindTabbarEvents(),this._initTabbarAnimation()},_initTabbarAnimation:function(){var b=!1,c=!1;a(document).bind("scrollstart.tabbar",function(d){a(d.target).find(".ui-tabbar").length&&(b=!0,c=!1)}),a(document).bind("scrollstop.tabbar",function(d){var e=a(d.target),f=a(d.target).find(".ui-tabbar"),g=a(d.target).find(".ui-tabbar li"),h=g.eq(0),i,j=-1;c=!0,f.length&&b==1&&(i=Math.abs(g.eq(0).offset().left),g.each(function(a){var b=g.eq(a).offset();Math.abs(b.left)<i&&(i=Math.abs(b.left),j=a,h=g.eq(a))}),e.length&&b==c&&j!=-1&&(b=!1,e.scrollview("scrollTo",-(window.innerWidth/f.data("defaultList")*j),0,357))),a(".ui-tabbar-divider-left").hide(),a(".ui-tabbar-divider-right").hide()})},_bindTabbarEvents:function(){var b=this.element;a(window).bind("orientationchange",function(c,d){var e=window.innerWidth||a(window).width(),f=window.innerHeight||a(window).height(),g=e>f&&e-f;g?b.removeClass("ui-portrait-tabbar").addClass("ui-landscape-tabbar"):b.removeClass("ui-landscape-tabbar").addClass("ui-portrait-tabbar")})},_setDisabled:function(a,b){this.element.find("li").eq(b).attr("disabled",a),this.element.find("li").eq(b).attr("aria-disabled",a)},disable:function(a){this._setDisabled(!0,a),this.element.find("li").eq(a).addClass("ui-disabled")},enable:function(a){this._setDisabled(!1,a),this.element.find("li").eq(a).removeClass("ui-disabled")}}),a(document).bind("pagecreate create",function(b){a(a.tizen.tabbar.prototype.options.initSelector,b.target).tabbar()})}(jQuery),function(a,b){a.widget("tizen.triangle",a.tizen.widgetex,{options:{extraClass:"",offset:null,color:null,location:"top",initSelector:":jqmData(role='triangle')"},_create:function(){var b=a("<div></div>",{"class":"ui-triangle"});a.extend(this,{_triangle:b}),this.element.addClass("ui-triangle-container").append(b)},_doCSS:function(){var b=this.options.location||"top",c=a.inArray(b,["top","bottom"])===-1?"top":"left",d={"border-bottom-color":"top"===b?this.options.color:"transparent","border-top-color":"bottom"===b?this.options.color:"transparent","border-left-color":"right"===b?this.options.color:"transparent","border-right-color":"left"===b?this.options.color:"transparent"};d[c]=this.options.offset,this._triangle.removeAttr("style").css(d)},_setOffset:function(b){this.options.offset=b,this.element.attr("data-"+(a.mobile.ns||"")+"offset",b),this._doCSS()},_setExtraClass:function(b){this._triangle.addClass(b),this.options.extraClass=b,this.element.attr("data-"+(a.mobile.ns||"")+"extra-class",b)},_setColor:function(b){this.options.color=b,this.element.attr("data-"+(a.mobile.ns||"")+"color",b),this._doCSS()},_setLocation:function(b){this.element.removeClass("ui-triangle-container-"+this.options.location).addClass("ui-triangle-container-"+b),this._triangle.removeClass("ui-triangle-"+this.options.location).addClass("ui-triangle-"+b),this.options.location=b,this.element.attr("data-"+(a.mobile.ns||"")+"location",b),this._doCSS()}}),a(document).bind("pagecreate create",function(b){a(a.tizen.triangle.prototype.options.initSelector,b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").triangle()})}(jQuery),function(a,b){a.widget("tizen.popupwindow",a.tizen.widgetex,{options:{theme:null,overlayTheme:"s",style:"custom",disabled:!1,shadow:!0,corners:!0,fade:!1,opacity:.7,widthRatio:.8612,transition:a.mobile.defaultDialogTransition,initSelector:":jqmData(role='popupwindow')"},_htmlProto:{source:["<div><div>"," <div id='popupwindow-screen' class='ui-selectmenu-screen ui-screen-hidden ui-popupwindow-screen'></div>"," <div id='popupwindow-container' class='ui-popupwindow ui-popupwindow-padding ui-selectmenu-hidden ui-overlay-shadow ui-corner-all'></div>","</div>","</div>"].join(""),ui:{screen:"#popupwindow-screen",container:"#popupwindow-container"}},_setStyle:function(){var a=this.element,b=a.attr("data-style");b&&(this.options.style=b),a.addClass(this.options.style),a.find(":jqmData(role='title')").wrapAll("<div class='popup-title'></div>"),a.find(":jqmData(role='text')").wrapAll("<div class='popup-text'></div>"),a.find(":jqmData(role='button-bg')").wrapAll("<div class='popup-button-bg'></div>"),a.find(":jqmData(role='check-bg')").wrapAll("<div class='popup-check-bg'></div>"),a.find(":jqmData(role='scroller-bg')").addClass("popup-scroller-bg"),a.find(":jqmData(role='text-bottom-bg')").wrapAll("<div class='popup-text-bottom-bg'></div>"),a.find(":jqmData(role='text-left')").wrapAll("<div class='popup-text-left'></div>"),a.find(":jqmData(role='text-right')").wrapAll("<div class='popup-text-right'></div>"),a.find(":jqmData(role='progress-bg')").wrapAll("<div class='popup-progress-bg'></div>")},_create:function(){console.warn("popupwindow() was deprecated. use popup() instead.");var b=this.element.closest(":jqmData(role='page')"),c=this;b.length===0&&(b=a("body")),this._ui.placeholder=a("<div><!-- placeholder for "+this.element.attr("id")+" --></div>").css("display","none").insertBefore(this.element),b.append(this._ui.screen),this._ui.container.insertAfter(this._ui.screen),this._ui.container.append(this.element),this._setStyle(),this._isOpen=!1,this._ui.screen.bind("vclick",function(a){return c.close(),!1}),this.element.bind("vclick",function(b){a(b.target).is("ui-btn-ctxpopup-close")&&c.close()})},destroy:function(){this.element.insertBefore(this._ui.placeholder),this._ui.placeholder.remove(),this._ui.container.remove(),this._ui.screen.remove(),this.element.triggerHandler("destroyed"),a.Widget.prototype.destroy.call(this)},_placementCoords:function(b,c,d,e){var f=a(window).height(),g=a(window).width(),h=e/2,i=parseFloat(this._ui.container.css("max-width")),j=c,k=f-c,l,m;return j>e/2&&k>e/2?l=c-h:l=j>k?f-e-30:30,d<i?m=(g-d)/2:(m=b-d/2,m<10?m=10:m+d>g&&(m=g-d-10)),{x:m,y:l}},_setPosition:function(c,d){var e=b===c?a(window).width()/2:c,f=b===d?a(window).height()/2:d,g,h=this.element.data("ctxpopup"),i,j,k,l,m,n,o,p,q,r,s;h||(i=a(window).width()*this.options.widthRatio,this._ui.container.css("width",i),this._ui.container.outerWidth()>a(window).width()&&this._ui.container.css({"max-width":a(window).width()-30})),g=this._placementCoords(e,f,this._ui.container.outerWidth(),this._ui.container.outerHeight()),j=this._ui.container.innerHeight(),k=this._ui.container.innerWidth(),l=a(window).height(),m=a(window).width(),n=f,o=l-f,p=j/2,q=parseFloat(this._ui.container.css("max-width")),r=(l-j)/2,!q||k<q?s=(m-k)/2:(s=e-k/2,s<30?s=30:s+k>m&&(s=m-k-30)),h&&(r=g.y,s=g.x),this._ui.container.css({top:r,left:s}),this._ui.screen.css("height",l)},open:function(b,c,d){var e=this,f=0;if(this._isOpen||this.options.disabled)return;a(document).find("*").each(function(){var b=a(this),c=parseInt(b.css("z-index"),10);b.is(e._ui.container)||b.is(e._ui.screen)||isNaN(c)||(f=Math.max(f,c))}),this._ui.screen.css("height",a(window).height()),d?this._ui.screen.css("opacity",0).removeClass("ui-screen-hidden"):(this._ui.removeClass("ui-screen-hidden"),this.options.fade?this._ui.screen.animate({opacity:this.options.opacity},"fast"):this._ui.screen.css({opacity:this.options.opacity})),this._setPosition(b,c),this.element.trigger("popupbeforeposition"),this._ui.container.removeClass("ui-selectmenu-hidden").addClass("in").animationComplete(function(){e.element.trigger("popupafteropen")}),this._isOpen=!0,this._reflow||(this._reflow=function(){if(!e._isOpen)return;e._setPosition(b,c)},a(window).bind("resize",this._reflow))},close:function(){if(!this._isOpen)return;this._reflow&&(a(window).unbind("resize",this._reflow),this._reflow=null);var b=this,c=function(){b._ui.screen.addClass("ui-screen-hidden"),b._isOpen=!1};this._ui.container.removeClass("in").addClass("reverse out"),this.options.transition==="none"?(this._ui.container.addClass("ui-selectmenu-hidden").removeAttr("style"),this.element.trigger("popupafterclose")):this._ui.container.animationComplete(function(){b._ui.container.removeClass("reverse out").addClass("ui-selectmenu-hidden").removeAttr("style"),b.element.trigger("popupafterclose")}),this.options.fade?this._ui.screen.animate({opacity:0},"fast",c):c()},_realSetTheme:function(a,b){var c=(a.attr("class")||"").split(" "),d=!0,e=null,f;while(c.length>0){e=c.pop(),f=e.match(/^ui-body-([a-z])$/);if(f&&f.length>1){e=f[1];break}e=null}a.removeClass("ui-body-"+e),(b||"").match(/[a-z]/)&&a.addClass("ui-body-"+b)},_setTheme:function(b){this._realSetTheme(this.element,b),this.options.theme=b,this.element.attr("data-"+(a.mobile.ns||"")+"theme",b)},_setOverlayTheme:function(b){this._realSetTheme(this._ui.container,b),this.options.overlayTheme=b,this.element.attr("data-"+(a.mobile.ns||"")+"overlay-theme",b)},_setShadow:function(b){this.options.shadow=b,this.element.attr("data-"+(a.mobile.ns||"")+"shadow",b),this._ui.container[b?"addClass":"removeClass"]("ui-overlay-shadow")},_setCorners:function(b){this.options.corners=b,this.element.attr("data-"+(a.mobile.ns||"")+"corners",b),this._ui.container[b?"addClass":"removeClass"]("ui-corner-all")},_setFade:function(b){this.options.fade=b,this.element.attr("data-"+(a.mobile.ns||"")+"fade",b)},_setTransition:function(b){this._ui.container.removeClass(this.options.transition||"").addClass(b),this.options.transition=b,this.element.attr("data-"+(a.mobile.ns||"")+"transition",b)},_setDisabled:function(b){a.Widget.prototype._setOption.call(this,"disabled",b),b&&this.close()}}),a.tizen.popupwindow.bindPopupToButton=function(a,b){if(a.length===0||b.length===0)return;var c=function(c){return b.jqmData("overlay-theme-set")||b.popupwindow("option","overlayTheme",a.jqmData("theme")),b.popupwindow("open",a.offset().left+a.outerWidth()/2,a.offset().top+a.outerHeight()/2),!1};(b.popupwindow("option","overlayTheme")||"").match(/[a-z]/)&&b.jqmData("overlay-theme-set",!0),a.attr({"aria-haspopup":!0,"aria-owns":a.attr("href")}).removeAttr("href").bind("vclick",c),b.bind("destroyed",function(){a.unbind("vclick",c)})},a(document).bind("pagecreate create",function(b){a(a.tizen.popupwindow.prototype.options.initSelector,b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").popupwindow(),a("a[href^='#']:jqmData(rel='popupwindow')",b.target).each(function(){a.tizen.popupwindow.bindPopupToButton(a(this),a(a(this).attr("href")))})})}(jQuery),function(a,b){a.widget("tizen.ctxpopup",a.tizen.widgetex,{options:a.extend({},a.tizen.popupwindow.prototype.options,{initSelector:":jqmData(show-arrow)"}),_htmlProto:{source:["<div><div id='outer' class='ui-ctxpopup'>"," <div id='top' class='ui-ctxpopup-row' data-role='triangle' data-location='top'></div>"," <div class='ui-ctxpopup-row'>"," <div id='left' class='ui-ctxpopup-cell' data-role='triangle' data-location='left'></div>"," <div id='container' class='ui-ctxpopup-cell'></div>"," <div id='right' class='ui-ctxpopup-cell' data-role='triangle' data-location='right'></div>"," </div>"," <div id='bottom' class='ui-ctxpopup-row' data-role='triangle' data-location='bottom'></div>","</div>","</div>"].join(""),ui:{outer:"#outer",container:"#container",arrow:{all:":jqmData(role='triangle')",l:"#left",t:"#top",r:"#right",b:"#bottom"}}},_create:function(){console.warn("ctxpopup() was deprecated. use popup() instead."),this.element.data("popupwindow")||this.element.popupwindow(),this.element.data("popupwindow")._ui.container.removeClass("ui-popupwindow-padding").append(this._ui.outer),this._ui.outer.trigger("create"),this._ui.container.addClass("ui-popupwindow-padding").append(this.element)},_setOption:function(b,c){a.tizen.popupwindow.prototype._setOption.apply(this.element.data("popupwindow"),arguments),this.options[b]=c}});var c=a.tizen.popupwindow.prototype.open,d=a.tizen.popupwindow.prototype._setOption,e=a.tizen.popupwindow.prototype._placementCoords;a.tizen.popupwindow.prototype._setOption=function(a,b){var c=this.element.data("ctxpopup"),e=!0,f;if(c){if("shadow"===a||"overlayTheme"===a||"corners"===a)f=this._ui.container,this._ui.container=c._ui.container,d.apply(this,arguments),this._ui.container=f,e=!1;c.options[a]=b}e&&d.apply(this,arguments)},a.tizen.popupwindow.prototype._placementCoords=function(c,d,f,g){function m(a,b,f){h._ui.arrow.all.hide(),h._ui.arrow[a].show();var g="b"===a||"t"===a,j=g?{point:"x",size:"cx",beg:"left",outerSize:"outerWidth",niceSize:"width",triangleSize:"height"}:{point:"y",size:"cy",beg:"top",outerSize:"outerHeight",niceSize:"height",triangleSize:"width"},k={cx:i._ui.container.width(),cy:i._ui.container.height()},l={cx:k.cx/2,cy:k.cy/2},m={x:c+l.cx*b,y:d+l.cy*f},n=e.call(i,m.x,m.y,k.cx,k.cy),o=h._ui.arrow[a].offset()[j.beg],p=h._ui.arrow[a][j.outerSize](!0),q=i.element.offset()[j.beg],r=i.element[j.outerSize](!0),s=h._ui.arrow[a][j.triangleSize](),t=Math.max(s+Math.max(0,q-o),Math.min(p-s-Math.max(0,o+p-(q+r)),p/2+m[j.point]-n[j.point]-l[j.size])),u={x:n.x+(g?t:0)+("r"===a?k.cx:0),y:n.y+(g?0:t)+("b"===a?k.cy:0)},v={actual:n,triangleOffset:t,absDiff:Math.abs(c-u.x)+Math.abs(d-u.y)};return h._ui.arrow[a].hide(),v}var h=this.element.data("ctxpopup"),i=this,j={},k,l;return h?(j={l:m("l",1,0),r:m("r",-1,0),t:m("t",0,1),b:m("b",0,-1)},a
-.each(j,function(a,c){if(k===b||c.absDiff<k)k=c.absDiff,l=a}),h._ui.arrow[l].show().triangle("option","offset",j[l].triangleOffset),j[l].actual):e.call(this,c,d,f,g)},a.tizen.popupwindow.prototype.open=function(b,d){var e=this.element.data("ctxpopup");e&&(this._setFade(!1),this._setShadow(!1),this._setCorners(!1),this._setOverlayTheme(null),this._setOption("overlayTheme",e.options.overlayTheme),e._ui.arrow.all.triangle("option","color",e._ui.container.css("background-color")),a(".ui-popupwindow").css("background","none")),c.call(this,b,d,!0)},a(document).bind("pagecreate create",function(b){var c=a(a.tizen.ctxpopup.prototype.options.initSelector,b.target);a.tizen.ctxpopup.prototype.enhanceWithin(b.target)})}(jQuery),function(a,b,c){a.widget("tizen.datetimepicker",a.tizen.widgetex,{options:{type:null,format:null,date:null,initSelector:"input[type='date'], input[type='datetime'], input[type='time'], :jqmData(role='datetimepicker')"},container:null,_calendar:function(){return b.Globalize.culture().calendars.standard},_value:{attr:"data-"+(a.mobile.ns||"")+"date",signal:"date-changed"},_daysInMonth:[31,28,31,30,31,30,31,31,30,31,30,31],_isLeapYear:function(a){return a%4?0:a%100?1:a%400?0:1},_makeTwoDigits:function(a){var b=a.toString(10);return a<10&&(b="0"+b),b},_setType:function(b){switch(b){case"datetime":case"date":case"time":this.options.type=b;break;default:this.options.type="datetime"}return this.element.attr("data-"+(a.mobile.ns?a.mobile.ns+"-":"")+"type",this.options.type),this.options.type},_setFormat:function(b){if(this.options.format==b)return;this.options.format=b,this.ui.children().remove();var c=this._parsePattern(b),d=document.createElement("div"),e,f,g,h,i=this;while(c.length>0){e=c.shift(),f='<span class="ui-datefield-%1" data-pat="'+e+'">%2</span>';switch(e){case"H":case"HH":case"h":case"hh":a(d).append(f.replace("%1","hour"));break;case"mm":case"m":this.options.type=="date"?a(d).append(f.replace("%1","month")):a(d).append(f.replace("%1","min"));break;case"ss":case"s":a(d).append(f.replace("%1","sec"));break;case"d":case"dd":a(d).append(f.replace("%1","day"));break;case"M":case"MM":case"MMM":case"MMMM":a(d).append(f.replace("%1","month"));break;case"yy":case"yyyy":a(d).append(f.replace("%1","year"));break;case"t":case"tt":h='<a href="#" class="ui-datefield-period" data-role="button" data-inline="true">period</a>',a(d).append(h);break;case"g":case"gg":a(d).append(f.replace("%1","era").replace("%2",this._calendar().eras.name));break;case"\t":a(d).append(f.replace("%1","tab").replace("%2",e));break;default:a(d).append(f.replace("%1","seperator").replace("%2",e))}}return this.ui.append(d),this.options.date&&this._setDate(this.options.date),this.ui.find(".ui-datefield-period").buttonMarkup().bind("vclick",function(a){return i._switchAmPm(i),!1}),this.element.attr("data-"+(a.mobile.ns?a.mobile.ns+"-":"")+"format",this.options.format),this.options.format},_setDate:function(b){function i(){return b.getMonth()+1}typeof b=="string"&&(b=new Date(b));var c=a("span,a",this.ui),d,e,f,g,h;for(h=0;h<c.length;h++){f=a(c[h]),d=f.attr("class").match(/ui-datefield-([\w]*)/),d||(d="");switch(d[1]){case"hour":e=b.getHours;break;case"min":e=b.getMinutes;break;case"sec":e=b.getSeconds;break;case"year":e=b.getFullYear;break;case"month":e=i;break;case"day":e=b.getDate;break;case"period":e=b.getHours()<12?this._calendar().AM[0]:this._calendar().PM[0],g=f.find(".ui-btn-text"),g.length==0?f.text(e):g.text()!=e&&g.text(e),e=null;break;default:e=null}e&&this._updateField(f,e.call(b))}return this.options.date=b,this._setValue(b),this.element.attr("data-"+(a.mobile.ns?a.mobile.ns+"-":"")+"date",this.options.date),this.options.date},destroy:function(){this.ui&&this.ui.remove(),this.element&&this.element.show()},value:function(a){function b(a,b){return b._makeTwoDigits(a.getHours())+":"+b._makeTwoDigits(a.getMinutes())+":"+b._makeTwoDigits(a.getSeconds())}function c(a,b){return(a.getFullYear()%1e4+1e4).toString().substr(1)+"-"+b._makeTwoDigits(a.getMonth()+1)+"-"+b._makeTwoDigits(a.getDate())}var d=null;if(a)d=this._setDate(a);else switch(this.options.type){case"time":d=b(this.options.date,this);break;case"date":d=c(this.options.date,this);break;default:d=c(this.options.date,this)+"T"+b(this.options.date,this)}return d},setValue:function(a){return console.warn("setValue was deprecated. use datetimepicker('option', 'date', value) instead."),this.value(a)},getValue:function(){return console.warn("getValue() was deprecated. use datetimepicker('value') instead."),this.value()},_updateField:function(a,b){if(!a||a.length==0)return;b==0&&(b="0");var c=a.jqmData("pat"),d,e,f=this;switch(c){case"H":case"HH":case"h":case"hh":d=b,c.charAt(0)=="h"&&(d>12?d-=12:d==0&&(d=12)),d=this._makeTwoDigits(d),e=d;break;case"m":case"M":case"d":case"s":e=b;break;case"mm":case"dd":case"MM":case"ss":e=this._makeTwoDigits(b);break;case"MMM":e=this._calendar().months.namesAbbr[b-1];break;case"MMMM":e=this._calendar().months.names[b-1];break;case"yy":e=this._makeTwoDigits(b%100);break;case"yyyy":b<10?b="000"+b:b<100?b="00"+b:b<1e3&&(b="0"+b),e=b}a.text()!=e&&(a.hasClass("ui-datefield-selected")?(a.addClass("out"),this._new_value=e,a.animationComplete(function(){a.text(f._new_value),a.addClass("in").removeClass("out"),a.animationComplete(function(){a.removeClass("in").removeClass("ui-datefield-selected")})})):a.text(e))},_switchAmPm:function(a){if(this._calendar().AM!=null){var b=new Date(this.options.date),c,d=432e5;b.getHours()>11&&(d=-d),b.setTime(b.getTime()+d),this._setDate(b)}},_parsePattern:function(a){var b=/\/|\s|dd|d|MMMM|MMM|MM|M|yyyy|yy|y|hh|h|HH|H|mm|m|ss|s|tt|t|f|gg|g|\'[\w\W]*\'$|[\w\W]/g,c,d;c=a.match(b);for(d=0;d<c.length;d++)c[d].charAt(0)=="'"&&(c[d]=c[d].substr(1,c[d].length-2));return c},changeTypeFormat:function(a,b){console.warn('changeTypeFormat() was deprecated. use datetimepicker("option", "type"|"format", value) instead'),a&&this._setType(a),b&&this._setFormat(b)},_create:function(){var c=this;this.element.is("input")&&function(a){var b,c,d;b=a.element.get(0).getAttribute("type"),a.options.type=b,c=a.element.get(0).getAttribute("value"),c&&(a.options.date=new Date(c))}(this);if(!this.options.format)switch(this.options.type){case"datetime":this.options.format=this._calendar().patterns.d+"\t"+this._calendar().patterns.t;break;case"date":this.options.format=this._calendar().patterns.d;break;case"time":this.options.format=this._calendar().patterns.t}this.options.date||(this.options.date=new Date),this.element.hide(),this.ui=a('<div class="ui-datefield"></div>'),a(this.element).after(this.ui),this._popup_open=!1,this.ui.bind("vclick",function(a){return c._showDataSelector(c,this,a.target),!1}),a.extend(this,{_globalHandlers:[{src:a(b),handler:{orientationchange:a.proxy(this,"_orientationHandler")}}]}),a.each(this._globalHandlers,function(a,b){b.src.bind(b.handler)})},_orientationHandler:function(){var a=this;return a._popup_open&&(a._popup_open=!1,a.container.popupwindow("close")),!1},_populateDataSelector:function(a,c){var d,e,f,g,h=b.range,i,j,k,l;switch(a){case"hour":c=="H"||c=="HH"?(d=h(0,23),g=h(0,23),f=this.options.date.getHours()):(d=h(1,12),f=this.options.date.getHours()-1,f>=11?(f-=12,g=h(13,23),g.push(12)):(g=h(1,11),g.push(0)),f<0&&(f=11)),c.length==2&&(d=d.map(this._makeTwoDigits)),e=d.length;break;case"min":case"sec":d=h(0,59),c.length==2&&(d=d.map(this._makeTwoDigits)),g=h(0,59),f=a=="min"?this.options.date.getMinutes():this.options.date.getSeconds(),e=d.length;break;case"year":j=1900,k=2100,g=h(j,k),f=this.options.date.getFullYear()-j,d=h(j,k),e=d.length;break;case"month":switch(c.length){case 1:d=h(1,12);break;case 2:d=h(1,12).map(this._makeTwoDigits);break;case 3:d=this._calendar().months.namesAbbr.slice();break;case 4:d=this._calendar().months.names.slice()}d.length==13&&d[12]==""&&d.pop(),g=h(1,d.length),f=this.options.date.getMonth(),e=d.length;break;case"day":l=this._daysInMonth[this.options.date.getMonth()],l==28&&(l+=this._isLeapYear(this.options.date.getFullYear())),d=h(1,l),c.length==2&&(d=d.map(this._makeTwoDigits)),g=h(1,l),f=this.options.date.getDate()-1,e=l}return{values:d,data:g,numItems:e,current:f}},_showDataSelector:function(d,e,f){f=a(f);var g=f.attr("class"),h=g?g.match(/ui-datefield-([\w]*)/):c,i,j,k,l,m,n,o,p,q,r,s,t,u,v=10,w=this;if(!g)return;if(!h)return;if(this._popup_open)return;f.not(".ui-datefield-seperator").addClass("ui-datefield-selected"),i=f.jqmData("pat"),j=d._populateDataSelector.call(d,h[1],i),k=j.values,l=j.numItems,m=j.current,n=j.data;if(k){p="data-"+(a.mobile.ns?a.mobile.ns+"-":"")+'val="';for(u=0;u<k.length;u++)o+='<li><a class="ui-link" '+p+n[u]+'">'+k[u]+"</a></li>";q=a("<ul></ul>"),r=a('<div class="ui-datetimepicker-selector" data-transition="fade" data-fade="false"></div>'),r.append(q).appendTo(e),s=r.ctxpopup(),s.parents(".ui-popupwindow").addClass("ui-datetimepicker"),t=a(o),a(t[m]).addClass("current"),r.jqmData("list",t),r.circularview(),d._reflow||(d._reflow=function(){r.circularview("reflow"),r.circularview("centerTo",".current",0)},a(b).bind("resize",d._reflow)),a(b).width()/2<f.offset().left&&(v=-10),s.popupwindow("open",f.offset().left+f.width()/2+v-b.pageXOffset,f.offset().top+f.height()-b.pageYOffset),this.container=s,this._popup_open=!0,r.bind("popupafterclose",function(c){d._reflow&&(a(b).unbind("resize",d._reflow),d._reflow=null),!f.hasClass("in")&&!f.hasClass("out")&&f.removeClass("ui-datefield-selected"),r.unbind("popupafterclose"),q.unbind("vclick"),a(d).unbind("update"),s.popupwindow("destroy"),r.remove(),w._popup_open=!1}),a(d).bind("update",function(a,b){var c=new Date(this.options.date),e,f=function(){c.setDate(1),c.setDate(c.getDate()-1)};switch(h[1]){case"min":c.setMinutes(b);break;case"hour":c.setHours(b);break;case"sec":c.setSeconds(b);break;case"year":e=c.getMonth(),c.setFullYear(b),c.getMonth()!=e&&f();break;case"month":c.setMonth(b-1),c.getMonth()==b&&f();break;case"day":c.setDate(b)}d._setDate(c),s.popupwindow("close")}),q.bind("click",function(b){if(a(b.target).is("a")){q.find(".current").removeClass("current"),a(b.target).parent().addClass("current");var c=a(b.target).jqmData("val");a(d).trigger("update",c)}}),r.circularview("centerTo",".current",500),r.bind("scrollend",function(c){d._reflow||(d._reflow=function(){r.circularview("reflow")},a(b).bind("resize",d._reflow))})}return e}}),a(document).bind("pagecreate create",function(b){a(a.tizen.datetimepicker.prototype.options.initSelector,b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").datetimepicker()})}(jQuery,this),function(a){a.tizen.frameworkData.pkgVersion="0.2.26"}(jQuery);
\ No newline at end of file
+function range(a,b,c){var d=[],e,f,g,h=c||1,i=!1;!isNaN(a)&&!isNaN(b)?(e=a,f=b):isNaN(a)&&isNaN(b)?(i=!0,e=a.charCodeAt(0),f=b.charCodeAt(0)):(e=isNaN(a)?0:a,f=isNaN(b)?0:b),g=e>f?!1:!0;if(g)while(e<=f)d.push(i?String.fromCharCode(e):e),e+=h;else while(e>=f)d.push(i?String.fromCharCode(e):e),e-=h;return d}var ensureNS=function(){var a={};return function(c){var d=c.split(".").reverse(),e="",f="",g="",h=d.length;while(--h>=0)g=d[h],e=e+(e.length>0?".":"")+g,a[e]||(a[e]=!0,f+="!window."+e+" && (window."+e+" = {});\n");f.length&&(new Function(f))()}}();(function(a,b){a.webgl={},a.webgl.shader={_vertexShader:null,_fragmentShader:null,deleteShaders:function(a){a.deleteShader(this._vertexShader),a.deleteShader(this._fragmentShader)},addShaderProgram:function(a,b,c,d){var e,f={},g={};return d?(f=this.loadShaderFile(b),g=this.loadShaderFile(c)):(f.source=b,g.source=c),this._vertexShader=this.getShader(a,a.VERTEX_SHADER,f),this._fragmentShader=this.getShader(a,a.FRAGMENT_SHADER,g),e=a.createProgram(),a.attachShader(e,this._vertexShader),a.attachShader(e,this._fragmentShader),a.linkProgram(e),a.getProgramParameter(e,a.LINK_STATUS)||window.alert("Could not initialize Shaders!"),e},loadShaderFile:function(b){var c=null;return a.ajax({async:!1,url:b,success:function(a){c={source:a}}}),c},getShader:function(a,b,c){var d;return!a||!b||!c?null:(d=a.createShader(b),a.shaderSource(d,c.source),a.compileShader(d),a.getShaderParameter(d,a.COMPILE_STATUS)?d:(window.alert(a.getShaderInfoLog(d)),a.deleteShader(d),null))}},a.webgl.buffer={attribBufferData:function(a,b){var c=a.createBuffer();return a.bindBuffer(a.ARRAY_BUFFER,c),a.bufferData(a.ARRAY_BUFFER,b,a.STATIC_DRAW),a.bindBuffer(a.ARRAY_BUFFER,null),c}}})(jQuery),function(a,b,c){var d=Math.PI/2,e=.001,f={},g=b.vec3,h=function(a,b){var c=[b[0]-a[0],b[1]-a[1],b[2]-a[2]],d=Math.sqrt(c[0]*c[0]+c[1]*c[1]+c[2]*c[2]);return d};f.base=function(){},f.base.prototype={points:[],step:e,length:0,levels:[],init:function(a){},calculateLevel:function(a){},calculateTotalLength:function(){},getPosition:function(a){},getPercent:function(a,b){},getAngle:function(a){}},f.bezier2d=function(){},f.bezier2d.prototype=a.extend(!0,{},f.base.prototype,{init:function(a){this.points=a.points,this.step=a.step||e,this.length=this.calculateTotalLength(),this.levels=this.calculateLevel(a.maxLevel)||[]},calculateLevel:function(a){var b=this.length,c=b/a,d=[],e;if(!a)return null;for(e=0;e<a;e+=1)d[a-e]=this.getPercent(0,c*e);return d},calculateTotalLength:function(){var a=this.step,b=this.getPosition(0),c=b,d=0,e;for(e=a;e<=1;e+=a)b=this.getPosition(e),d+=h(c,b),c=b;return d},getPosition:function(a){var b=this.points,c=function(a,b,c,d,e){return Math.pow(1-e,3)*a+3*e*Math.pow(1-e,2)*b+3*Math.pow(e,2)*(1-e)*c+Math.pow(e,3)*d},d=[c(b[0][0],b[1][0],b[2][0],b[3][0],a),c(b[0][2],b[1][2],b[2][2],b[3][2],a)];return[d[0],0,d[1]]},getPercent:function(a,b){var c=this.step,d=this.getPosition(a=a||0),e=d,f=a+b,g=0,i;for(i=a+c;i<=1;i+=c){d=this.getPosition(i),g+=h(e,d);if(g>=f)return i;e=d}return 1},getAngle:function(a){var b=this.points,c=function(a,b,c,d,e){return 3*e*e*(-a+3*b-3*c+d)+6*e*(a-2*b+c)+3*(-a+b)},e=c(b[0][0],b[1][0],b[2][0],b[3][0],a),f=c(b[0][2],b[1][2],b[2][2],b[3][2],a);return Math.atan2(e,f)-d}}),f.bspline=function(){},f.bspline.prototype=a.extend(!0,{},f.base.prototype,{_degree:3,_numberOfControls:0,_knotVectors:[],_numberOfKnots:0,init:function(a){this.points=a.points,this.step=a.step||e,this._numberOfPoints=this.points.length-1,this._numberOfKnots=this._numberOfPoints+this._degree+1;var b=1/(this._numberOfKnots-2*this._degree),c=b,d=0;while(d<=this._numberOfKnots)d<=this._degree?this._knotVectors.push(0):d<this._numberOfKnots-this._degree+1?(this._knotVectors.push(c),c+=b):this._knotVectors.push(1),d+=1;this.length=this.calculateTotalLength(),this.levels=this.calculateLevel(a.maxLevel)||[]},_Np:function(a,b,c){var d=this._knotVectors,e=0,f=0,g=0,h=function(a,b){return d[b]<=a&&a<d[b+1]?1:0};return c===1?(e=h(a,b),f=h(a,b+1)):(e=this._Np(a,b,c-1),f=this._Np(a,b+1,c-1)),g=d[b+c]-d[b],e*=g!==0?(a-d[b])/g:0,g=d[b+c+1]-d[b+1],f*=g!==0?(d[b+c+1]-a)/g:0,e+f},calculateLevel:function(a){var b=this.length,c=b/a,d=[],e;if(!a)return null;for(e=0;e<a;e+=1)d[a-e]=this.getPercent(0,c*e);return d},calculateTotalLength:function(){var a=this.step,b=this.getPosition(0),c=b,d=0,e;for(e=a;e<=1;e+=a)b=this.getPosition(e),d+=h(c,b),c=b;return d},getPosition:function(a){var b=[],c,d,e;a=a.toFixed(4);for(d=0;d<3;d+=1){e=0;for(c=0;c<=this._numberOfPoints;c+=1)e+=this.points[c][d]*this._Np(a,c,this._degree);b[d]=e}return b},getPercent:function(a,b){var c=this.step,d=this.getPosition(a=a||0),e=d,f=a+b,g=0,i;for(i=a+c;i<=1;i+=c){d=this.getPosition(i),g+=h(e,d);if(g>=f)return i;e=d}return 1},getAngle:function(a){var b=this.getPosition(a),c=this.getPosition(a+.001),d=g.normalize(g.direction(b,c)),e=g.dot(d,[1,0,0]);return Math.acos(e)+Math.PI}}),a.motionpath=function(a,b){var c=new f[a];return c.init(b),c}}(jQuery,window),function(a,b){ensureNS("jQuery.mobile.tizen"),jQuery.extend(jQuery.mobile.tizen,{_widgetPrototypes:{},loadPrototype:function(c,d){function h(a){return a.replace(/\$\{FRAMEWORK_ROOT\}/g,g)}function i(a,b){var c;for(var d in a)typeof a[d]=="string"?(c=a[d],a[d]=b.find(a[d]),c.substring(0,1)==="#"&&a[d].removeAttr("id")):typeof a[d]=="object"&&(a[d]=i(a[d],b));return a}var e=b,f=a("script[data-framework-version][data-framework-root][data-framework-theme]"),g=f.attr("data-framework-root")+"/"+f.attr("data-framework-version")+"/";if(typeof c=="string"){e=a.mobile.tizen._widgetPrototypes[c];if(e===b){var j=g+"proto-html"+"/"+f.attr("data-framework-theme");a.ajax({url:j+"/"+c+".prototype.html",async:!1,dataType:"html"}).success(function(b,d,f){a.mobile.tizen._widgetPrototypes[c]=a("<div>").html(h(b)),e=a.mobile.tizen._widgetPrototypes[c].clone()})}}else c.key!==b&&(e=a.mobile.tizen._widgetPrototypes[c.key]),e===b?c.proto!==b&&(e=a("<div>").html(h(c.proto)),c.key!==b&&(a.mobile.tizen._widgetPrototypes[c.key]=e.clone())):e=e.clone();return e!=b&&d!=b&&(e=i(d,e)),e}})}(jQuery),function(a,b,c,d){function g(){if(f)return;e=c.createElement("canvas"),f=e.getContext("2d")}function h(a){var c=b.FileError,d="";switch(a.code){case c.QUOTA_EXCEEDED_ERR:d="QUOTA_EXCEEDED_ERR";break;case c.NOT_FOUND_ERR:d="NOT_FOUND_ERR";break;case c.SECURITY_ERR:d="SECURITY_ERR";break;case c.INVALID_MODIFICATION_ERR:d="INVALID_MODIFICATION_ERR";break;case c.INVALID_STATE_ERR:d="INVALID_STATE_ERR";break;default:d="Unknown Error"}return d}function i(a){var b=a.replace(/\//gi,"_");return b}function j(a,b,c,d,e){var f=0,g=0,h=0,i=0,j=a/c,k=b/d,l=Math.max(j,k);return e?(f=c,g=d):(l>1?(f=a/l,g=b/l):(f=a,g=b),h=(c-f)/2,i=(d-g)/2),{w:f,h:g,x:h,y:i}}function k(a,b,c,d){var h,i;return g(),e.width=b,e.height=c,h=j(a.width,a.height,b,c,d),f.fillStyle="#000000",f.fillRect(0,0,b,c),f.drawImage(a,h.x,h.y,h.w,h.h),i=e.toDataURL(),i}var e,f;a.imageloader={_grantedBytes:1048576,getThumbnail:function(a,b){function e(a){var c=h(a);b&&b(c==="NOT_FOUND_ERR"?c:null)}var c,d;c=i(a);try{d=localStorage.getItem(c),b&&b(d===null?"NOT_FOUND_ERR":d)}catch(f){b&&b(f.type==="non_object_property_load"?"NOT_FOUND_ERR":null)}},setThumbnail:function(a,b,c,d,e){function l(a){var c=h(a);b&&b(c==="NOT_FOUND_ERR"?c:null)}var f,g,j;c=c||128,d=d||128,e=e||!0,f=new Image,f.onload=function(){g=i(a),j=k(this,c,d,e);try{localStorage.setItem(g,j),b&&b(j)}catch(f){b&&b(f.type==="non_object_property_load"?"NOT_FOUND_ERR":null)}},f.src=a},removeThumbnail:function(a){function c(a){h(a)}var b;b=i(a);try{localStorage.removeItem(b)}catch(d){throw d}}}}(jQuery,window,document),function(a,b,c){a.widget("tizen.gallery",a.mobile.widget,{options:{flicking:!1,duration:500},dragging:!1,moving:!1,max_width:0,max_height:0,org_x:0,org_time:null,cur_img:null,prev_img:null,next_img:null,images:[],images_hold:[],index:0,align_type:null,direction:1,container:null,orientationEventFire:!1,_resize:function(a){var b=this.images[a],c=this.images[a].width(),d=this.images[a].height(),e=0,f,g=this.max_width-e,h=this.max_height-e;f=d/c,c>g&&(b.width(g),b.height(g*f)),d=b.height(),d>h&&(b.height(h),b.width(h/f))},_align:function(a,b){var c=this.images[a],d=0;if(!b)return;if(!b.length)return;this.align_type=="middle"?d=(this.max_height-c.height())/2:this.align_type=="bottom"?d=this.max_height-c.height():d=0,b.css("top",d+"px")},_attach:function(a,b){var d=this,e=function(){d._resize(a),d._align(a,b)},f=function(){if(d.images[a]===c)return;if(!d.images[a].height()){setTimeout(f,10);return}e()};if(!b)return;if(!b.length)return;if(a<0)return;if(!this.images.length)return;if(a>=this.images.length)return;b.css("display","block"),b.css("visibility","hidden"),b.append(this.images[a]),f()},_detach:function(a,b){if(!b)return;if(!b.length)return;if(a<0)return;if(a>=this.images.length)return;b.css("display","none"),this.images[a].removeAttr("style"),this.images[a].detach()},_detach_all:function(){var a;for(a=0;a<this.images.length;a++)this.images[a].detach()},_drag:function(a){var b,c;if(!this.dragging)return;if(this.options.flicking===!1){b=this.org_x-a;if(b<0&&!this.prev_img.length)return;if(b>0&&!this.next_img.length)return}c=a-this.org_x,this._moveLeft(this.cur_img,c+"px"),this.next_img.length&&this._moveLeft(this.next_img,c+this.window_width+"px"),this.prev_img.length&&this._moveLeft(this.prev_img,c-this.window_width+"px")},_move:function(a){var b=this.org_x-a,c=0,d,e,f;if(b==0)return;b>0?c=b<this.max_width*.45?0:1:c=-b<this.max_width*.45?0:1,c||(d=Date.now()-this.org_time,Math.abs(b)/d>1&&(c=1)),c&&(b>0&&this.next_img.length?(this._detach(this.index-1,this.prev_img),this.prev_img=this.cur_img,this.cur_img=this.next_img,this.next_img=this.next_img.next(),this.index++,this.next_img.length&&(this._moveLeft(this.next_img,this.window_width+"px"),this._attach(this.index+1,this.next_img)),this.direction=1):b<0&&this.prev_img.length&&(this._detach(this.index+1,this.next_img),this.next_img=this.cur_img,this.cur_img=this.prev_img,this.prev_img=this.prev_img.prev(),this.index--,this.prev_img.length&&(this._moveLeft(this.prev_img,-this.window_width+"px"),this._attach(this.index-1,this.prev_img)),this.direction=-1)),e=this.options.duration,f=this,this.moving=!0,setTimeout(function(){f.moving=!1},e-25),this._moveLeft(this.cur_img,"0px",e),this.next_img.length&&this._moveLeft(this.next_img,this.window_width+"px",e),this.prev_img.length&&this._moveLeft(this.prev_img,-this.window_width+"px",e)},_add_event:function(){var a=this,b;this.container.bind("vmousemove",function(b){b.preventDefault();if(a.moving)return;if(!a.dragging)return;a._drag(b.pageX)}),this.container.bind("vmousedown",function(b){b.preventDefault();if(a.moving)return;a.dragging=!0,a.org_x=b.pageX,a.org_time=Date.now()}),this.container.bind("vmouseup",function(b){if(a.moving)return;a.dragging=!1,a._move(b.pageX)}),this.container.bind("vmouseout",function(b){if(a.moving)return;if(!a.dragging)return;if(b.pageX<20||b.pageX>a.max_width-20)a._move(b.pageX),a.dragging=!1})},_del_event:function(){this.container.unbind("vmousemove"),this.container.unbind("vmousedown"),this.container.unbind("vmouseup"),this.container.unbind("vmouseout")},_setTranslateposition:function(b,c){var d,e=null,f=this;return a.support.cssTransform3d?d="translate3d("+c+", 0px, 0px)":d="translate("+c+", 0px)",e={"-moz-transform":d,"-webkit-transform":d,"-ms-transform":d,"-o-transform":d,transform:d},b.css(e),b},_hidePrevNext:function(){var a=this;a.next_img&&a.next_img.css("visibility","hidden"),a.prev_img&&a.prev_img.css("visibility","hidden")},_hideCur:function(){var a=this;a.cur_img&&a.cur_img.css("visibility","hidden")},_moveLeft:function(b,d,e){var f,g="",h=null,i=this;return a.support.cssTransform3d?f="translate3d("+d+", 0px, 0px)":f="translate("+d+", 0px)",e!==c&&(g="-webkit-transform "+e/1e3+"s ease"),h={"-moz-transform":f,"-webkit-transform":f,"-ms-transform":f,"-o-transform":f,transform:f},g!==""&&(h["-webkit-transition"]=g,d=="0px"?b.one("webkitTransitionEnd",i._hidePrevNext):b.one("webkitTransitionEnd",i._hideCur)),d=="0px"&&b.css("visibility","visible"),b.css(h),b},_show:function(){this.window_width=a(b).width(),this.max_width=this._get_width(),this.max_height=this._get_height(),this.container.css("height",this.max_height),this.cur_img=a("div").find(".ui-gallery-bg:eq("+this.index+")"),this.prev_img=this.cur_img.prev(),this.next_img=this.cur_img.next(),this._attach(this.index-1,this.prev_img),this._attach(this.index,this.cur_img),this._attach(this.index+1,this.next_img),this.cur_img.css("visibility","visible"),this.prev_img.length&&this._setTranslateposition(this.prev_img,-this.window_width+"px"),this._moveLeft(this.cur_img,"0px"),this.next_img.length&&this._setTranslateposition(this.next_img,this.window_width+"px")},show:function(){if(!this.images.length)return;this._show(),this._add_event()},_hide:function(){this._detach(this.index-1,this.prev_img),this._detach(this.index,this.cur_img),this._detach(this.index+1,this.next_img)},hide:function(){this._hide(),this._del_event()},_get_width:function(){return a(this.element).width()},_get_height:function(){var c=a(this.element).parentsUntil("ui-page"),d=c.children(".ui-content"),e=c.children(".ui-header").outerHeight()||0,f=c.children(".ui-footer").outerHeight()||0,g=parseFloat(d.css("padding-top"))+parseFloat(d.css("padding-bottom")),h=a(b).height()-e-f-g;return h},_create:function(){var c,d=this,e,f=0;a(this.element).wrapInner('<div class="ui-gallery"></div>'),a(this.element).find("img").wrap('<div class="ui-gallery-bg"></div>'),this.container=a(this.element).find(".ui-gallery"),c=a("div").find(".ui-gallery-bg:first");while(c.length)this.images[f]=c.find("img"),c=c.next(),f++;this._detach_all(),e=parseInt(a(this.element).jqmData("index"),10),e||(e=0),e<0&&(e=0),e>=this.images.length&&(e=this.images.length-1),this.index=e,this.align_type=a(this.element).jqmData("vertical-align"),a.extend(this,{_globalHandlers:[{src:a(b),handler:{orientationchange:a.proxy(this,"_orientationHandler"),resize:a.proxy(this,"_resizeHandler")}}]}),a.each(this._globalHandlers,function(a,b){b.src.bind(b.handler)})},_update:function(){var b,c,d;while(this.images_hold.length)b=this.images_hold.shift(),c=a('<div class="ui-gallery-bg"></div>'),d=a('<img src="'+b+'"></div>'),c.append(d),this.container.append(c),this.images.push(d);this._detach_all()},_resizeHandler:function(){var a=this;a.orientationEventFire&&(a.refresh(),a.orientationEventFire=!1)},_orientationHandler:function(){var a=this;a.refresh(),a.orientationEventFire=!0},refresh:function(a){return this._update(),this._hide(),a===c&&(a=this.index),a<0&&(a=0),a>=this.images.length&&(a=this.images.length-1),this.index=a,this._show(),this.index},add:function(a){this.images_hold.push(a)},remove:function(b){var d;b===c&&(b=this.index);if(b<0||b>=this.images.length)return;b==this.index?(d=this.cur_img,this.index==0?this.direction=1:this.index==this.images.length-1&&(this.direction=-1),this.direction<0?(this.cur_img=this.prev_img,this.prev_img=this.prev_img.prev(),this.prev_img.length&&(this._moveLeft(this.prev_img,-this.window_width+"px"),this._attach(b-2,this.prev_img)),this.index--):(this.cur_img=this.next_img,this.next_img=this.next_img.next(),this.next_img.length&&(this._moveLeft(this.next_img,this.window_width+"px"),this._attach(b+2,this.next_img))),this._moveLeft(this.cur_img,"0px",this.options.duration)):b==this.index-1?(d=this.prev_img,this.prev_img=this.prev_img.prev(),this.prev_img.length&&(this._moveLeft(this.prev_img,-this.window_width+"px"),this._attach(b-1,this.prev_img)),this.index--):b==this.index+1?(d=this.next_img,this.next_img=this.next_img.next(),this.next_img.length&&(this._moveLeft(this.next_img,this.window_width+"px"),this._attach(b+1,this.next_img))):d=a("div").find(".ui-gallery-bg:eq("+b+")"),this.images.splice(b,1),d.detach()},empty:function(){this.images.splice(0,this.images.length),this.container.find(".ui-gallery-bg").detach()},length:function(){return this.images.length},value:function(a){if(a===c)return this.index;this.refresh(a)},destory:function(){a(b).unbind("resize",this._resizeHandler),a(b).unbind("orientationchange",this._orientationHandler)}}),a(document).bind("pagecreate create",function(b){a(b.target).find(":jqmData(role='gallery')").gallery()}),a(document).bind("pageshow",function(b){a(b.target).find(":jqmData(role='gallery')").gallery("show")}),a(document).bind("pagebeforehide",function(b){a(b.target).find(":jqmData(role='gallery')").gallery("hide")})}(jQuery,this),function(a,b){a(document).bind("pagecreate create",function(b){a(":jqmData(role='label')",b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").each(function(){a(this).addClass("jquery-mobile-ui-label").html(a("<span>",{"class":"jquery-mobile-ui-label-text"}).text(a(this).text()))})})}(jQuery),function(a,b){a.widget("tizen.listdivider",a.mobile.widget,{options:{initSelector:":jqmData(role='list-divider')",folded:!1,listDividerLine:!0},_create:function(){var c=this.element,d=!0,e,f=!0,g=c.attr("data-style");c.data("line")===!1&&(this.options.listDividerLine=!1),c.data("folded")===!0&&(this.options.folded=!0);if(g==b||g==="normal"||g==="check")this.options.folded?c.buttonMarkup():c.wrapInner("<span class='ui-btn-text'></span>"),this.options.listDividerLine&&(e="<span class='ui-divider-normal-line'></span>",this.options.folded?a(e).appendTo(c.children(".ui-btn-inner")):a(e).appendTo(c));c.bind("vclick",function(a,b){})}}),a(document).bind("pagecreate create",function(b){a(a.tizen.listdivider.prototype.options.initSelector,b.target).listdivider()})}(jQuery),function(a,b,c,d){function e(){this.vertices=[-1,-1,0,1,-1,0,1,1,0,-1,1,0],this.textureCoords=[1,0,0,0,0,1,1,1],this.normalVectors=[0,0,1,0,0,1,0,0,1,0,0,1],this.texture=null,this.textureBuffer=null,this.textureBufferItemSize=0,this.mashOrder=[],this.mvMatrix=null,this.level=-1,this.targetLevel=0,this.drawable=!1,this.image=null,this.imageID=0}var f=!1,g={},h,i,j,k,l=function(){if(f)return;c.initGlMatrix(g),h=["attribute vec3 aVertexPosition;","attribute vec2 aTextureCoord;","attribute vec3 aVertexNormal;","uniform mat4 uMoveMatrix;","uniform mat4 uPerspectiveMatrix;","uniform mat3 nNormalMatrix;","uniform vec3 uAmbientColor;","uniform vec3 uLightDirection;","uniform vec3 uDirectionColor;","uniform vec3 uLightDirection_first;","uniform vec3 uLightDirection_second;","varying vec2 vTextureCoord;","varying vec3 vLightWeight;","varying vec4 vFogWeight;","void main(void) {","\tvec4 v_Position = uMoveMatrix * vec4(aVertexPosition, 1.0);","\tgl_Position = uPerspectiveMatrix * v_Position;","\tvTextureCoord = aTextureCoord;","\tfloat fog = 1.0 - ((gl_Position.z + 1.5) / 60.0);","\tvFogWeight = clamp( vec4( fog, fog, fog, 1.0), 0.6, 1.0);","\tvec3 transNormalVector = nNormalMatrix * aVertexNormal;","\tfloat vLightWeightFirst = 0.0;","\tfloat vLightWeightSecond = max( dot(transNormalVector, uLightDirection_second), 0.0 );","\tvLightWeight = uAmbientColor + uDirectionColor * vLightWeightSecond;","}"].join("\n"),i=["precision mediump float;","varying vec2 vTextureCoord;","varying vec3 vLightWeight;","uniform sampler2D uSampler;","varying vec4 vFogWeight;","void main(void) {","\tvec4 TextureColor;","\tif ( vTextureCoord.s <= 0.01 || vTextureCoord.s >= 0.99 || vTextureCoord.t <= 0.01 || vTextureCoord.t >= 0.99 ) {","\t\tTextureColor = vec4(1.0, 1.0, 1.0, 0.5);","\t} else {","\t\tTextureColor = texture2D(uSampler, vec2(vTextureCoord.s, vTextureCoord.t));","\t}","\tTextureColor *= vFogWeight;","\tgl_FragColor = vec4(TextureColor.rgb * vLightWeight, TextureColor.a);","}"].join("\n"),j=typeof c.Float32Array!="undefined"?c.Float32Array:typeof c.WebGLFloatArray!="undefined"?c.WebGLFloatArray:Array,k=typeof c.Uint16Array!="undefined"?c.Uint16Array:Array,f=!0},m=function(a){return a*Math.PI/180},n=function(b){var c,d,e=["experimental-webgl","webkit-3d","webgl","moz-webgl"];for(d=0;d<e.length;d+=1)try{c=b.getContext(e[d]);if(c)break}catch(f){a(b).html("Unfortunately, there's a WebGL compatibility problem. </br> You may want to check your system settings.");return}return c},o=function(a){var b=c.setTimeout(a,1e3/60);return b},p=function(a){c.clearTimeout(a)};a.widget("tizen.gallery3d",a.mobile.widget,{options:{thumbnailCache:!1},_MAX_ITEM_COUNT:28,_ANIMATION_END:999,_DURATION_DEFAULT:300,_DURATION_FIRST:1600,_VIEWPORT_WIDTH:1024,_VIEWPORT_HEIGHT:456,_DIRECTION_LEFT:-1,_DIRECTION_RIGHT:1,_gl:null,_shaderProgram:null,_positionBuffer:null,_textureCoordBuffer:null,_normalVectorBuffer:null,_nodes:null,_pMatrix:null,_animationID:0,_dragInterval:0,_startTime:0,_sumTime:0,_lightsPositionStack:[[0,0,-1],[-0.2,0,.7]],_path:null,_swipeThresholdOfBasetimeGap:a.support.touch?30:70,_swipeThresholdOfSensitivity:a.support.touch?2:10,_canvas:null,_imageList:[],_maxDrawLength:0,_firstImageNumber:0,_lastImageNumber:0,_create:function(){var b=this,c=b.element,e=b.options;l(),b._canvas=a("<canvas class='ui-gallery3d-canvas'></canvas>"),c.addClass("ui-gallery3d").append(b._canvas),b._addBehavier(),b._dragInterval=1e3/30,a.each(b.options,function(a,c){b.options[a]=d,b._setOption(a,c)})},destroy:function(){this._final(),a.mobile.widget.prototype.destroy.call(this)},_setOption:function(b,c){switch(b){case"thumbnailCache":typeof c=="string"?c=c==="true"?!0:!1:c=!!c,this._reset()}a.mobile.widget.prototype._setOption.call(this,b,c)},_init:function(b){var c=this,d=[[40,0,-48],[-12,0,-40],[24,0,-9],[-5,0,-5]],e;b=b||c._canvas;if(!b)return;c._gl=c._gl||c._initGL(b[0]);if(!c._gl)return;if(!c._imageList)return;c._shaderProgram=c._shaderProgram||c._initShader(c._gl);if(!c._shaderProgram)return;c._imageList.length>c._MAX_ITEM_COUNT&&(c._firstImageNumber=c._imageList.length-1,c._lastImageNumber=c._MAX_ITEM_COUNT-1),c._nodes=c._initBuffers(c._gl,c._shaderProgram),c._initTextures(c._gl,c._nodes),c._path=a.motionpath("bezier2d",{points:d,maxLevel:c._MAX_ITEM_COUNT});for(e=0;e<c._nodes.length;e+=1)c._path.levels[e]=c._path.levels[e+1]||0,c._nodes[e].level=e},_final:function(b){var c=this,d=c._gl;if(!d)return;c._stop(),b=b||c._canvas,a(c._nodes).each(function(a){var b=c._nodes[a];d.deleteTexture(b.texture),b.texture=null}),c._nodes=null,d.deleteBuffer(c._positionBuffer),c._positionBuffer=null,d.deleteBuffer(c._textureCoordBuffer),c._textureCoordBuffer=null,d.deleteBuffer(c._normalVectorBuffer),c._normalVectorBuffer=null,a.webgl.shader.deleteShaders(d),d.deleteProgram(c._shaderProgram),c._shaderProgram=null,c._gl=d=null},_addBehavier:function(){var b=this,c=b.element,d=b._canvas,e=a.support.touch?"touchstart":"mousedown",f=(a.support.touch?"touchmove":"mousemove")+".gallery3d",g=(a.support.touch?"touchend":"mouseup")+".gallery3d",h=(a.support.touch?"touchleave":"mouseout")+".gallery3d";d.on("webglcontextlost",function(a){a.preventDefault()}).on("webglcontextrestored",function(a){b._init()}).on(e,function(d){var e=0,i=0,j=20,k=[j],l=[j],m=0,n=0,o=!1,p=0;d.preventDefault(),d.stopPropagation();if(b._imageList.length<=1)return;b._stop(),i=a.support.touch?d.originalEvent.changedTouches[0].pageX:d.pageX,p=a.now();for(e=0;e<j;e+=1)k[e]=i,l[e]=a.now();m+=1,c.on(f,function(c){var d,e,f;c.preventDefault(),c.stopPropagation(),d=a.support.touch?c.originalEvent.changedTouches[0].pageX:c.pageX,e=i-d,k[m]=d,l[m]=a.now(),f=l[m]-p,m=(m+1)%j,Math.abs(e)>=10&&f>=b._dragInterval&&(o!==(e<0?b._DIRECTION_RIGHT:b._DIRECTION_LEFT)&&(n=0,o=e<0?b._DIRECTION_RIGHT:b._DIRECTION_LEFT),n+=Math.abs(e)/100,n>=1?(b._setPosition(b._ANIMATION_END,o),n=0):b._setPosition(n,o),b._drawScene(),i=d,p=a.now())}).on(g,function(d){var f=0,g=-1,h=0,p=0,q=0,r=0,s=0,t=0,u=0,v=!0,w;d.preventDefault(),d.stopPropagation(),f=a.now()-b._swipeThresholdOfBasetimeGap,s=a.support.touch?d.originalEvent.changedTouches[0].pageX:d.pageX,u=i-s,i=0;for(e=0;e<j;e+=1){h=(m+e)%j;if(l[h]>f){g=h;break}}g<0&&(v=!1);if(v){p=g;for(e=0;e<j;e+=1){p=(p-1+j)%j;if(l[p]<l[g])break}if(e===j||f<l[p])v=!1}v&&(q=(f-l[p])/(l[g]-l[p]),r=(1-q)*k[p]+q*k[g],Math.abs(r-s)<b._swipeThresholdOfSensitivity&&(r=s),t=parseInt((s-r)/(a.now()-f),10)),v&&t?(w=t<0?b._DIRECTION_LEFT:b._DIRECTION_RIGHT,b._run(w,Math.abs(t),n)):o!==0&&n&&b._animate(null,b._DURATION_DEFAULT*(1-n),o,0,n),c.unbind(".gallery3d")}).on(h,function(a){c.trigger(g)})})},_initGL:function(a){var b=this,c=g.mat4,d;return d=n(a),d?(d.enable(d.BLEND),d.blendFunc(d.SRC_ALPHA,d.ONE_MINUS_SRC_ALPHA),d.enable(d.DEPTH_TEST),d.depthFunc(d.LEQUAL),a.width=b._VIEWPORT_WIDTH,a.height=b._VIEWPORT_HEIGHT,d.viewportWidth=a.width,d.viewportHeight=a.height,d.viewport(0,0,d.viewportWidth,d.viewportHeight),b._pMatrix=c.create(),c.perspective(40,d.viewportWidth/d.viewportHeight,.1,1e4,b._pMatrix),d.clearColor(.15,.15,.15,1),d.clear(d.COLOR_BUFFER_BIT|d.DEPTH_BUFFER_BIT),d):null},_initShader:function(b){var c=this,d;return d=a.webgl.shader.addShaderProgram(c._gl,h,i),b.useProgram(d),d.vertexPositionAttr=b.getAttribLocation(d,"aVertexPosition"),b.enableVertexAttribArray(d.vertexPositionAttr),d.textureCoordAttr=b.getAttribLocation(d,"aTextureCoord"),b.enableVertexAttribArray(d.textureCoordAttr),d.vertexNormalAttr=b.getAttribLocation(d,"aVertexNormal"),b.enableVertexAttribArray(d.vertexNormalAttr),d.perspectiveMU=b.getUniformLocation(d,"uPerspectiveMatrix"),d.transformMU=b.getUniformLocation(d,"uMoveMatrix"),d.sampleUniform=b.getUniformLocation(d,"uSampler"),d.normalMU=b.getUniformLocation(d,"nNormalMatrix"),d.ambientColorU=b.getUniformLocation(d,"uAmbientColor"),d.lightDirU_first=b.getUniformLocation(d,"uLightDirection_first"),d.lightDirU_second=b.getUniformLocation(d,"uLightDirection_second"),d.directionColorU=b.getUniformLocation(d,"uDirectionColor"),d},_initBuffers:function(b,c){var d=this,f=0,g=0,h=[],i=[],l=[],m=[],n=d._MAX_ITEM_COUNT;for(f=0;f<d._imageList.length+1;f+=1)m[f]=new e,a.merge(h,m[f].vertices),a.merge(i,m[f].textureCoords),a.merge(l,m[f].normalVectors),m[f].textureBuffer=b.createBuffer(),b.bindBuffer(b.ELEMENT_ARRAY_BUFFER,m[f].textureBuffer),g=f*4,m[f].meshOrder=[g,g+1,g+2,g+2,g+3,g],b.bufferData(b.ELEMENT_ARRAY_BUFFER,new k(m[f].meshOrder),b.STATIC_DRAW),b.bindBuffer(b.ELEMENT_ARRAY_BUFFER,null),m[f].textureBufferItemSize=6;return d._positionBuffer=a.webgl.buffer.attribBufferData(b,new j(h)),d._positionBuffer.itemSize=3,d._textureCoordBuffer=a.webgl.buffer.attribBufferData(b,new j(i)),d._textureCoordBuffer.itemSize=2,d._normalVectorBuffer=a.webgl.buffer.attribBufferData(b,new j(l)),d._normalVectorBuffer.itemSize=3,b.uniform3f(c.ambientColorU,.1,.1,.1),b.uniform3f(c.directionColorU,1,1,1),m},_initTextures:function(b,c){var d=this;a(c).each(function(a){var e=c[a],f;if(!d._imageList[a])return!1;f=d._imageList[a].src,e.texture=b.createTexture(),d._loadImage(f,a,a,b,c)})},_loadImage:function(b,c,d,e,f){var g=this,h=!1,i,j;e=e||g._gl,f=f||g._nodes,h=h||!1,j=f[c],j.image=j.image||new Image,a(j.image).one("load",function(a){g._bindTexture(e,j,this,h),j.imageID=d,g._animationID||g._setPosition(0,0)}),g.options.thumbnailCache?a.imageloader.getThumbnail(b,function(c){c==="NOT_FOUND_ERR"?a.imageloader.setThumbnail(b,function(a){a&&a.length>30?(j.image.src=a,h=!0):j.image.src=b}):c&&c.length>30?(j.image.src=c,h=!0):j.image.src=b}):j.image.src=b},_bindTexture:function(a,b,c,d){if(!b||!b.texture)return;a.pixelStorei(a.UNPACK_FLIP_Y_WEBGL,!0),a.bindTexture(a.TEXTURE_2D,b.texture),a.texImage2D(a.TEXTURE_2D,0,a.RGBA,a.RGBA,a.UNSIGNED_BYTE,c),d?(a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MAG_FILTER,a.LINEAR),a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MIN_FILTER,a.LINEAR_MIPMAP_NEAREST),a.generateMipmap(a.TEXTURE_2D)):(a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MAG_FILTER,a.LINEAR),a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MIN_FILTER,a.LINEAR)),a.texParameteri(a.TEXTURE_2D,a.TEXTURE_WRAP_S,a.CLAMP_TO_EDGE),a.texParameteri(a.TEXTURE_2D,a.TEXTURE_WRAP_T,a.CLAMP_TO_EDGE),b.texture.loaded=!0,a.bindTexture(a.TEXTURE_2D,null)},_setPosition:function(a,b){var c=this,d=g.mat4,e=c._nodes,f=c._imageList,h=f.length,i=c._MAX_ITEM_COUNT,j=h>i?i:h,k=0,l=0,n=0,o=0,p=0,q=0,r=0,s=0,t=c._path,u=0;k=b>=0?j+1:j,e[l].level||(e[l].level=j);for(l=0;l<j;l+=1)e[l].mvMatrix||(e[l].mvMatrix=d.create()),b>0&&e[l].level>=j&&(e[l].level=0),q=t.levels[e[l].level],s=(e[l].level+k+b)%k,r=t.levels[s],h>i&&(b>0&&s===1&&c._firstImageNumber!==e[l].imageID?c._loadImage(f[c._firstImageNumber].src,l,c._firstImageNumber):b<0&&s===k-1&&c._lastImageNumber!==e[l].imageID&&c._loadImage(f[c._lastImageNumber].src,l,c._lastImageNumber)),d.identity(e[l].mvMatrix),d.translate(e[l].mvMatrix,[-2,-2,1]),d.rotate(e[l].mvMatrix,m(19),[1,0,0]),n=q+(r-q)*(a>1?1:a),a>=c._ANIMATION_END&&(e[l].level=s||j,n=t.levels[e[l].level]),a<c._ANIMATION_END&&b<=0&&e[l].level<1?e[l].drawable=!1:e[l].drawable=!0,a===c._ANIMATION_END&&e[l].level===1&&c.element.trigger("select",f[e[l].imageID],e[l].imageID),o=t.getPosition(n),p=t.getAngle(n),d.translate(e[l].mvMatrix,o),d.rotate(e[l].mvMatrix,p,[0,1,0]);h>i&&a>=c._ANIMATION_END&&(c._firstImageNumber=(c._firstImageNumber-b)%h,c._firstImageNumber<0&&(c._firstImageNumber=h-1),c._lastImageNumber=(c._lastImageNumber-b)%h,c._lastImageNumber<0&&(c._lastImageNumber=h-1)),c._drawScene()},_drawScene:function(){if(!this._gl||!this._shaderProgram)return;var a=this,b=a._gl,c=a._shaderProgram,d=a._nodes,e=d.length,f;b.clear(b.COLOR_BUFFER_BIT|b.DEPTH_BUFFER_BIT),b.bindBuffer(b.ARRAY_BUFFER,a._positionBuffer),b.vertexAttribPointer(c.vertexPositionAttr,a._positionBuffer.itemSize,b.FLOAT,!1,0,0),b.bindBuffer(b.ARRAY_BUFFER,a._textureCoordBuffer),b.vertexAttribPointer(c.textureCoordAttr,a._textureCoordBuffer.itemSize,b.FLOAT,!1,0,0),b.bindBuffer(b.ARRAY_BUFFER,a._normalVectorBuffer),b.vertexAttribPointer(c.vertexNormalAttr,a._normalVectorBuffer.itemSize,b.FLOAT,!1,0,0);for(f=0;f<e;f+=1)d[f].drawable&&a._drawElement(a._pMatrix,d[f])},_drawElement:function(a,b){var c=this,d=c._gl,e=g.vec3,f=g.mat3,h=g.mat4,i=c._shaderProgram,j=b.mvMatrix,k=b.texture,l=b.textureBuffer,m=b.textureBufferItemSize,n=c._lightsPositionStack,o,p;if(!j)return;d.activeTexture(d.TEXTURE0),k&&k.loaded&&d.bindTexture(d.TEXTURE_2D,k),d.uniform1i(i.sampleUniform,0),o=e.create(),e.normalize(n[0],o),e.scale(o,-8),d.uniform3fv(i.lightDirU_first,o),e.normalize(n[1],o),e.scale(o,-1),d.uniform3fv(i.lightDirU_second,o),d.bindBuffer(d.ELEMENT_ARRAY_BUFFER,l),d.uniformMatrix4fv(i.perspectiveMU,!1,a),d.uniformMatrix4fv(i.transformMU,!1,j),p=f.create(),h.toInverseMat3(j,p),f.transpose(p),d.uniformMatrix3fv(i.normalMU,!1,p),d.drawElements(d.TRIANGLES,m,d.UNSIGNED_SHORT,0),d.bindBuffer(d.ARRAY_BUFFER,null),d.bindBuffer(d.ELEMENT_ARRAY_BUFFER,null),d.bindTexture(d.TEXTURE_2D,null)},_animate:function(b,c,d,e,f,g){var h=this,i=a.now(),j,k=0;b=b||"linear",f=f||0,g=g||0;if(h._sumTime>=c){h._setPosition(h._ANIMATION_END,d),h._stop();return}if(h._startTime===0)h._startTime=i;else{h._sumTime=i-h._startTime,j=a.easing[b](h._sumTime/c,h._sumTime,f,e+1,c),k=parseInt(Math.abs(j),10);if(g!==k){h._setPosition(h._ANIMATION_END,d),g=k,e-g>=0?h._animate(b,c,d,e,f,g):h._stop();return}h._setPosition(j-g,d)}h._animationID=o(function(){h._animate(b,c,d,e,f,g)})},_run:function(a,b,c){var d=this,e=b||0,f=d._DURATION_DEFAULT*(e+1);if(d._imageList.length<=1)return;c=c||0,f=f>=0?f:0,d._animationID&&(d._setPosition(d._ANIMATION_END,a),d._stop()),d._animate("easeOutExpo",f,a,e,c)},_reset:function(){if(!this._canvas||!this._gl)return;this._final(),this._init(),this.refresh()},_stop:function(){this._animationID&&p(this._animationID),this._animationID=0,this._startTime=0,this._sumTime=0},next:function(){this._run(this._DIRECTION_LEFT,0)},prev:function(){this._run(this._DIRECTION_RIGHT,0)},refresh:function(){var a=this.element,b=a.find("canvas.ui-gallery3d-canvas");b.width()!==a.width()&&b.width(a.width()),this._animationID||this._setPosition(0,0)},select:function(a){var b=this._nodes,c,d,e,f=null,g=0,h=0;a&&this._animationID&&this._stop();for(d in b)if(b[d].level===1){f=this._imageList[b[d].imageID],e=b[d].imageID;break}if(!a)return f;if(a<0&&a>=this._imageList.length)return;g=a-e,h=g>0?this._DIRECTION_LEFT:g<0?this._DIRECTION_RIGHT:0,h&&this._run(h,Math.abs(g)-1)},add:function(a,b){if(!a)return;typeof a=="string"&&(a={src:a}),b=b||0;if(typeof b!="number"&&b<0&&b>=this._imageList.length)return;this._imageList.splice(b,0,a),this._gl&&this._reset()},remove:function(a){a=a||0;if(typeof a!="number"&&a<0&&a>=this._imageList.length)return;this._imageList.splice(a,1),this._gl&&this._reset()},clearThumbnailCache:function(){if(!this._nodes||this._nodes.length<=0)return;var b,c;for(b=0;b<this._imageList.length;b+=1)c=this._imageList[b].src,a.imageloader.removeThumbnail(c)},empty:function(){this._imageList=[],this._reset()},length:function(){return this._imageList.length}}),a(b).on("pagecreate create",function(b){a(":jqmData(role='gallery3d')").gallery3d()}).on("pagechange",function(b){a(b.target).find(".ui-gallery3d").gallery3d("refresh")}),a(c).on("resize orientationchange"
+,function(b){a(".ui-page-active").find(".ui-gallery3d").gallery3d("refresh")})}(jQuery,document,window),function(a,b,c,d){function e(c){var d=a(c),e=d.children(".ui-content"),f=d.children(".ui-header").outerHeight()||0,g=d.children(".ui-footer").outerHeight()||0,h=parseFloat(e.css("padding-top")),i=parseFloat(e.css("padding-bottom")),j=a(b).height();e.height(j-(f+g)-(h+i))}function f(b){this.options=a.extend({},b),this.easing="easeOutQuad",this.reset()}function h(){return Date.now()}var g={scrolling:0,overshot:1,snapback:2,done:3};jQuery.widget("tizen.scrollview",jQuery.mobile.widget,{options:{direction:null,timerInterval:10,scrollDuration:1e3,overshootDuration:250,snapbackDuration:500,moveThreshold:30,moveIntervalThreshold:150,scrollMethod:"translate",startEventName:"scrollstart",updateEventName:"scrollupdate",stopEventName:"scrollstop",eventType:a.support.touch?"touch":"mouse",showScrollBars:!0,overshootEnable:!1,outerScrollEnable:!1,overflowEnable:!0,scrollJump:!1},_getViewHeight:function(){return this._$view.height()},_getViewWidth:function(){return this._$view.width()},_makePositioned:function(a){a.css("position")==="static"&&a.css("position","relative")},_create:function(){var b,c=this;this._$clip=a(this.element).addClass("ui-scrollview-clip"),this._$clip.children(".ui-scrollview-view").length?this._$view=this._$clip.children(".ui-scrollview-view"):this._$view=this._$clip.wrapInner("<div></div>").children().addClass("ui-scrollview-view"),this.options.scrollMethod==="translate"&&this._$view.css("transform")===d&&(this.options.scrollMethod="position"),this._$clip.css("overflow","hidden"),this._makePositioned(this._$clip),this._makePositioned(this._$view),this._$view.css({left:0,top:0}),this._view_height=this._getViewHeight(),this._sx=0,this._sy=0,b=this.options.direction,this._hTracker=b!=="y"?new f(this.options):null,this._vTracker=b!=="x"?new f(this.options):null,this._timerInterval=this.options.timerInterval,this._timerID=0,this._timerCB=function(){c._handleMomentumScroll()},this._add_event(),this._add_scrollbar(),this._add_scroll_jump(),this._add_overflow_indicator()},_startMScroll:function(a,b){var c=!1,d=this.options.scrollDuration,e=this._hTracker,f=this._vTracker,g,h;this._$clip.trigger(this.options.startEventName);if(e){g=this._$clip.width(),h=this._getViewWidth();if((this._sx===0&&a>0||this._sx===-(h-g)&&a<0)&&h>g)return;e.start(this._sx,a,d,h>g?-(h-g):0,0),c=!e.done()}if(f){g=this._$clip.height(),h=this._getViewHeight();if((this._sy===0&&b>0||this._sy===-(h-g)&&b<0)&&h>g)return;f.start(this._sy,b,d,h>g?-(h-g):0,0),c=c||!f.done()}c?this._timerID=setTimeout(this._timerCB,this._timerInterval):this._stopMScroll()},_stopMScroll:function(){this._timerID&&(this._$clip.trigger(this.options.stopEventName),clearTimeout(this._timerID)),this._timerID=0,this._vTracker&&this._vTracker.reset(),this._hTracker&&this._hTracker.reset(),this._hideScrollBars(),this._hideOverflowIndicator()},_handleMomentumScroll:function(){var a=!1,b=0,c=0,d=0,e=this,f=this._vTracker,g=this._hTracker;if(this._outerScrolling)return;f&&(f.update(this.options.overshootEnable),c=f.getPosition(),a=!f.done(),f.getRemained()>this.options.overshootDuration&&(d=this._getViewHeight()-this._$clip.height(),f.isAvail()?f.isMin()?this._outerScroll(c-f.getRemained()/3,d):f.isMax()&&this._outerScroll(f.getRemained()/3,d):this._speedY>0?this._outerScroll(f.getRemained()/3,d):this._outerScroll(c-f.getRemained()/3,d))),g&&(g.update(this.options.overshootEnable),b=g.getPosition(),a=a||!g.done()),this._setScrollPosition(b,c),this._$clip.trigger(this.options.updateEventName,[{x:b,y:c}]),a?this._timerID=setTimeout(this._timerCB,this._timerInterval):this._stopMScroll()},_setElementTransform:function(b,c,e,f){var g,h;!f||f===d?h="none":h="-webkit-transform "+f/1e3+"s ease-out",a.support.cssTransform3d?g="translate3d("+c+","+e+", 0px)":g="translate("+c+","+e+")",b.css({"-moz-transform":g,"-webkit-transform":g,"-ms-transform":g,"-o-transform":g,transform:g,"-webkit-transition":h})},_setEndEffect:function(a){var b=this._getViewHeight()-this._$clip.height();if(this._softkeyboard){this._effect_dir?this._outerScroll(-b-this._softkeyboardHeight,b):this._outerScroll(this._softkeyboardHeight,b);return}if(a==="in"){if(this._endEffect)return;this._endEffect=!0,this._setOverflowIndicator(this._effect_dir),this._showOverflowIndicator()}else if(a==="out"){if(!this._endEffect)return;this._endEffect=!1}else this._endEffect=!1,this._setOverflowIndicator(),this._showOverflowIndicator()},_setCalibration:function(a,b){if(this.options.overshootEnable){this._sx=a,this._sy=b;return}var c=this._$view,d=this._$clip,e=this._directionLock,f=0,g=0;e!=="y"&&this._hTracker&&(g=c.width()-d.width(),a>=0?this._sx=0:a<-g?this._sx=-g:this._sx=a,g<0&&(this._sx=0)),e!=="x"&&this._vTracker&&(f=this._getViewHeight()-d.height(),b>0?(this._sy=0,this._effect_dir=0,this._setEndEffect("in")):b<-f?(this._sy=-f,this._effect_dir=1,this._setEndEffect("in")):(this._endEffect&&this._sy!==b&&this._setEndEffect(),this._sy=b),f<0&&(this._sy=0))},_setScrollPosition:function(a,b,c){var d=this._$view,e=this.options.scrollMethod,f=this._$vScrollBar,g=this._$hScrollBar,h;this._setCalibration(a,b),a=this._sx,b=this._sy,e==="translate"?this._setElementTransform(d,a+"px",b+"px",c):d.css({left:a+"px",top:b+"px"}),f&&(h=f.find(".ui-scrollbar-thumb"),e==="translate"?this._setElementTransform(h,"0px",-b/this._getViewHeight()*h.parent().height()+"px",c):h.css("top",-b/this._getViewHeight()*100+"%")),g&&(h=g.find(".ui-scrollbar-thumb"),e==="translate"?this._setElementTransform(h,-a/d.width()*h.parent().width()+"px","0px",c):h.css("left",-a/d.width()*100+"%"))},_outerScroll:function(c,e){var f=this,g=a(b).scrollTop()-b.screenTop,i=0,j=this.options.snapbackDuration,k=h(),l;if(!this.options.outerScrollEnable)return;if(this._$clip.jqmData("scroll")!=="y")return;if(this._outerScrolling)return;if(c>0)i=b.screenTop?b.screenTop:-c;else{if(!(c<-e))return;i=-c-e}l=function(){var c=h()-k;c>=j?(b.scrollTo(0,g+i),f._outerScrolling=d,f._stopMScroll()):(ec=a.easing.easeOutQuad(c/j,c,0,1,j),b.scrollTo(0,g+i*ec),f._outerScrolling=setTimeout(l,f._timerInterval))},this._outerScrolling=setTimeout(l,f._timerInterval)},_scrollTo:function(b,c,d){var e=this,f=h(),g=a.easing.easeOutQuad,i=this._sx,j=this._sy,k=b-i,l=c-j,m;b=-b,c=-c,m=function(){var a=h()-f,n;a>=d?(e._timerID=0,e._setScrollPosition(b,c)):(n=g(a/d,a,0,1,d),e._setScrollPosition(i+k*n,j+l*n),e._timerID=setTimeout(m,e._timerInterval))},this._timerID=setTimeout(m,this._timerInterval)},scrollTo:function(a,b,c){this._stopMScroll(),this._didDrag=!1,!c||this.options.scrollMethod==="translate"?this._setScrollPosition(a,b,c):this._scrollTo(a,b,c)},getScrollPosition:function(){return{x:-this._sx,y:-this._sy}},skipDragging:function(a){this._skip_dragging=a},_getScrollHierarchy:function(){var b=[],c;return this._$clip.parents(".ui-scrollview-clip").each(function(){c=a(this).jqmData("scrollview"),c&&b.unshift(c)}),b},_getAncestorByDirection:function(a){var b=this._getScrollHierarchy(),c=b.length,d,e;while(0<c--){d=b[c],e=d.options.direction;if(!e||e===a)return d}return null},_handleDragStart:function(b,c,d){this._stopMScroll(),this._didDrag=!1,this._skip_dragging=!1;var e=a(b.target),f=this,g=this._$clip,h=this.options.direction;this._is_button=e.is(".ui-btn")||e.is(".ui-btn-text")||e.is(".ui-btn-inner")||e.is(".ui-btn-inner .ui-icon");if(e.parents(".ui-slider").length||e.is(".ui-slider")){this._skip_dragging=!0;return}e.is("textarea")&&e.bind("scroll",function(){f._skip_dragging=!0,e.unbind("scroll")}),this._is_inputbox=e.is(":input")||e.parents(":input").length>0,this._is_inputbox&&e.one("resize.scrollview",function(){d>g.height()&&f.scrollTo(-c,f._sy-d+g.height(),f.options.snapbackDuration)}),this.options.eventType==="mouse"&&!this._is_inputbox&&!this._is_button&&b.preventDefault(),this._lastX=c,this._lastY=d,this._startY=d,this._doSnapBackX=!1,this._doSnapBackY=!1,this._speedX=0,this._speedY=0,this._directionLock="",this._lastMove=0,this._enableTracking(),this._set_scrollbar_size()},_propagateDragMove:function(a,b,c,d,e){this._hideScrollBars(),this._hideOverflowIndicator(),this._disableTracking(),a._handleDragStart(b,c,d),a._directionLock=e,a._didDrag=this._didDrag},_handleDragMove:function(b,c,d){if(this._skip_dragging)return;if(!this._dragging)return;!this._is_inputbox&&!this._is_button&&b.preventDefault();var e=this.options.moveThreshold,f=c-this._lastX,g=d-this._lastY,i=this.options.direction,j=null,k,l,m,n,o,p,q;this._lastMove=h();if(!this._directionLock){k=Math.abs(f),l=Math.abs(g);if(k<e&&l<e)return!1;k<l&&k/l<.5?j="y":k>l&&l/k<.5&&(j="x");if(i&&j&&i!==j){m=this._getAncestorByDirection(j);if(m)return this._propagateDragMove(m,b,c,d,j),!1}this._directionLock=i||j||"none"}o=this._sx,p=this._sy,q=this._directionLock;if(q!=="y"&&this._hTracker){k=this._sx,this._speedX=f,o=k+f,this._doSnapBackX=!1,n=o>0||o<this._maxX;if(n&&q==="x"){m=this._getAncestorByDirection("x");if(m)return this._setScrollPosition(o>0?0:this._maxX,p),this._propagateDragMove(m,b,c,d,j),!1;o=k+f/2,this._doSnapBackX=!0}}if(q!=="x"&&this._vTracker){if(Math.abs(this._startY-d)<e&&q!=="xy")return;l=this._sy,this._speedY=g,p=l+g,this._doSnapBackY=!1,n=p>0||p<this._maxY;if(n&&q==="y"){m=this._getAncestorByDirection("y");if(m)return this._setScrollPosition(o,p>0?0:this._maxY),this._propagateDragMove(m,b,c,d,j),!1;p=l+g/2,this._doSnapBackY=!0}}this.options.overshootEnable===!1&&(this._doSnapBackX=!1,this._doSnapBackY=!1),this._lastX=c,this._lastY=d,this._setScrollPosition(o,p),this._didDrag===!1&&(this._didDrag=!0,this._showScrollBars(),this._showOverflowIndicator(),this._$clip.parents(".ui-scrollview-clip").each(function(){a(this).scrollview("skipDragging",!0)}))},_handleDragStop:function(a){var b=this;if(this._skip_dragging)return;var c=this._lastMove,d=h(),e=c&&d-c<=this.options.moveIntervalThreshold,f=this._hTracker&&this._speedX&&e?this._speedX:this._doSnapBackX?1:0,g=this._vTracker&&this._speedY&&e?this._speedY:this._doSnapBackY?1:0,i=this.options.direction,j,k;return f||g?this._setGestureScroll(f,g)||this._startMScroll(f,g):(this._hideScrollBars(),this._hideOverflowIndicator()),this._disableTracking(),this._endEffect&&setTimeout(function(){b._setEndEffect("out"),b._hideScrollBars(),b._hideOverflowIndicator()},300),!this._didDrag},_setGestureScroll:function(a,b){var c=this,e=function(){clearTimeout(c._gesture_timer),c._gesture_dir=0,c._gesture_timer=d},f={top:0,bottom:1,left:2,right:3};return!b&&!a?!1:(Math.abs(a)>Math.abs(b)?dir=a>0?f.left:f.right:dir=b>0?f.top:f.bottom,this._gesture_timer?this._gesture_dir!==dir?(e(),!1):!1:(this._gesture_dir=dir,this._gesture_timer=setTimeout(function(){e()},1e3),!1))},_enableTracking:function(){this._dragging=!0},_disableTracking:function(){this._dragging=!1},_showScrollBars:function(a){var b="ui-scrollbar-visible",c=this;if(!this.options.showScrollBars)return;if(this._scrollbar_showed)return;this._$vScrollBar&&this._$vScrollBar.addClass(b),this._$hScrollBar&&this._$hScrollBar.addClass(b),this._scrollbar_showed=!0,a&&setTimeout(function(){c._hideScrollBars()},a)},_hideScrollBars:function(){var a="ui-scrollbar-visible";if(!this.options.showScrollBars)return;if(!this._scrollbar_showed)return;this._$vScrollBar&&this._$vScrollBar.removeClass(a),this._$hScrollBar&&this._$hScrollBar.removeClass(a),this._scrollbar_showed=!1},_setOverflowIndicator:function(a){a===1?(this._opacity_top="0",this._opacity_bottom="0.8"):a===0?(this._opacity_top="0.8",this._opacity_bottom="0"):(this._opacity_top="0.5",this._opacity_bottom="0.5")},_showOverflowIndicator:function(){if(!this.options.overflowEnable||!this._overflowAvail||this._softkeyboard)return;this._overflow_top.animate({opacity:this._opacity_top},300),this._overflow_bottom.animate({opacity:this._opacity_bottom},300),this._overflow_showed=!0},_hideOverflowIndicator:function(){if(!this.options.overflowEnable||!this._overflowAvail||this._softkeyboard)return;if(this._overflow_showed===!1)return;this._overflow_top.animate({opacity:0},300),this._overflow_bottom.animate({opacity:0},300),this._overflow_showed=!1,this._setOverflowIndicator()},_add_event:function(){var c=this,e=this._$clip,f=this._$view;this.options.eventType==="mouse"?(this._dragEvt="mousedown mousemove mouseup click mousewheel",this._dragCB=function(a){switch(a.type){case"mousedown":return c._handleDragStart(a,a.clientX,a.clientY);case"mousemove":return c._handleDragMove(a,a.clientX,a.clientY);case"mouseup":return c._handleDragStop(a);case"click":return!c._didDrag;case"mousewheel":var b=c.getScrollPosition();c.scrollTo(-b.x,-(b.y-a.originalEvent.wheelDelta))}}):(this._dragEvt="touchstart touchmove touchend click",this._dragCB=function(a){var b=a.originalEvent.touches;switch(a.type){case"touchstart":if(b.length!=1)return;return c._handleDragStart(a,b[0].pageX,b[0].pageY);case"touchmove":if(b.length!=1)return;return c._handleDragMove(a,b[0].pageX,b[0].pageY);case"touchend":if(b.length!=0)return;return c._handleDragStop(a);case"click":return!c._didDrag}}),f.bind(this._dragEvt,this._dragCB),f.bind("keydown",function(f){var g,h,i=a(b).scrollTop()-b.screenTop,j;if(f.keyCode==9)return!1;g=e.find(".ui-focus");if(g===d)return;h=g.offset().top-i,j=e.offset().top+e.height()-g.height(),c._softkeyboard&&(j-=c._softkeyboardHeight),(h<e.offset().top||h>j)&&c.scrollTo(0,c._sy-(h-e.offset().top-g.height()));return}),f.bind("keyup",function(d){var f,g,h,j=a(b).scrollTop()-b.screenTop,k;if(d.keyCode!=9)return;f=a(this).find(":input");for(i=0;i<f.length;i++){if(!a(f[i]).hasClass("ui-focus"))continue;i+1==f.length?g=a(f[0]):g=a(f[i+1]),h=g.offset().top-j,k=e.offset().top+e.height()-g.height(),c._softkeyboard&&(k-=c._softkeyboardHeight),(h<0||h>k)&&c.scrollTo(0,c._sy-h+g.height()+e.offset().top,0),g.focus();break}return!1}),e.bind("updatelayout",function(a){var b,d,f=c._getViewHeight();if(!e.height()||!f){c.scrollTo(0,0,0);return}b=e.height()-f,d=f-c._view_height,c._view_height=f;if(d==0||d>e.height()/2)return;b>0?c.scrollTo(0,0,0):c._sy-b<=-d?c.scrollTo(0,c._sy,c.options.snapbackDuration):c._sy-b<=d+c.options.moveThreshold&&c.scrollTo(0,b,c.options.snapbackDuration)}),a(b).bind("resize",function(b){var d,f=c._getViewHeight();if(a(".ui-page-active").get(0)!==e.closest(".ui-page").get(0))return;if(!e.height()||!f)return;d=e.find(".ui-focus"),d&&d.trigger("resize.scrollview"),setTimeout(function(){c._sy<e.height()-c._getViewHeight()&&c.scrollTo(0,e.height()-c._getViewHeight(),c.options.overshootDuration)},260),c._view_height=f}),a(b).bind("vmouseout",function(d){var f=!1;if(a(".ui-page-active").get(0)!==e.closest(".ui-page").get(0))return;if(!c._dragging)return;if(d.pageX<0||d.pageX>a(b).width())f=!0;if(d.pageY<0||d.pageY>a(b).height())f=!0;f&&(c._hideScrollBars(),c._hideOverflowIndicator(),c._disableTracking())}),this._softkeyboard=!1,this._softkeyboardHeight=0,b.addEventListener("softkeyboardchange",function(d){if(a(".ui-page-active").get(0)!==e.closest(".ui-page").get(0))return;c._softkeyboard=d.state==="on"?!0:!1,c._softkeyboardHeight=parseInt(d.height)*(a(b).width()/b.screen.availWidth)}),e.closest(".ui-page").bind("pageshow",function(a){setTimeout(function(){c._view_height=c._getViewHeight(),c._set_scrollbar_size(),c._setScrollPosition(c._sx,c._sy),c._showScrollBars(2e3)},0)})},_add_scrollbar:function(){var a=this._$clip,b='<div class="ui-scrollbar ui-scrollbar-',c='"><div class="ui-scrollbar-track"><div class="ui-scrollbar-thumb"></div></div></div>';if(!this.options.showScrollBars)return;this._vTracker&&(a.append(b+"y"+c),this._$vScrollBar=a.children(".ui-scrollbar-y")),this._hTracker&&(a.append(b+"x"+c),this._$hScrollBar=a.children(".ui-scrollbar-x")),this._scrollbar_showed=!1},_add_scroll_jump:function(){var b=this._$clip,c=this,d,e;if(!this.options.scrollJump)return;this._vTracker&&(d=a('<div class="ui-scroll-jump-top-bg"><div data-role="button" data-inline="true" data-icon="scrolltop" data-style="box"></div></div>'),b.append(d).trigger("create"),d.bind("vclick",function(){c.scrollTo(0,0,c.options.overshootDuration)})),this._hTracker&&(e=a('<div class="ui-scroll-jump-left-bg"><div data-role="button" data-inline="true" data-icon="scrollleft" data-style="box"></div></div>'),b.append(e).trigger("create"),e.bind("vclick",function(){c.scrollTo(0,0,c.options.overshootDuration)}))},_add_overflow_indicator:function(){if(!this.options.overflowEnable)return;this._overflow_top=a('<div class="ui-overflow-indicator-top"></div>'),this._overflow_bottom=a('<div class="ui-overflow-indicator-bottom"></div>'),this._$clip.append(this._overflow_top),this._$clip.append(this._overflow_bottom),this._opacity_top="0.5",this._opacity_bottom="0.5",this._overflow_showed=!1},_set_scrollbar_size:function(){var a=this._$clip,b=this._$view,c=0,d=0,e=0,f=0,g;if(!this.options.showScrollBars)return;this._hTracker&&(c=a.width(),d=b.width(),this._maxX=c-d,this._maxX>0&&(this._maxX=0),this._$hScrollBar&&d&&(g=this._$hScrollBar.find(".ui-scrollbar-thumb"),g.css("width",c>=d?"0":(Math.floor(c/d*100)||1)+"%")));if(this._vTracker){e=a.height(),f=this._getViewHeight(),this._maxY=e-f;if(this._maxY>0||f===0)this._maxY=0;if(this._$vScrollBar&&f||f===0)g=this._$vScrollBar.find(".ui-scrollbar-thumb"),g.css("height",e>=f?"0":(Math.floor(e/f*100)||1)+"%"),this._overflowAvail=!!g.height()}}}),a.extend(f.prototype,{start:function(a,b,c,d,e){var f=a<d||a>e?g.snapback:g.scrolling,i;this.state=b!==0?f:g.done,this.pos=a,this.speed=b,this.duration=this.state===g.snapback?this.options.snapbackDuration:c,this.minPos=d,this.maxPos=e,this.fromPos=this.state===g.snapback?this.pos:0,i=this.pos<this.minPos?this.minPos:this.maxPos,this.toPos=this.state===g.snapback?i:0,this.startTime=h()},reset:function(){this.state=g.done,this.pos=0,this.speed=0,this.minPos=0,this.maxPos=0,this.duration=0,this.remained=0},update:function(b){var c=this.state,d=h(),e=this.duration,f=d-this.startTime,i,j,k;return c===g.done?this.pos:(f=f>e?e:f,this.remained=e-f,c===g.scrolling||c===g.overshot?(i=this.speed*(1-a.easing[this.easing](f/e,f,0,1,e)),j=this.pos+i,k=c===g.scrolling&&(j<this.minPos||j>this.maxPos),k&&(j=j<this.minPos?this.minPos:this.maxPos),this.pos=j,c===g.overshot?(b||(this.state=g.done),f>=e&&(this.state=g.snapback,this.fromPos=this.pos,this.toPos=j<this.minPos?this.minPos:this.maxPos,this.duration=this.options.snapbackDuration,this.startTime=d,f=0)):c===g.scrolling&&(k&&b?(this.state=g.overshot,this.speed=i/2,this.duration=this.options.overshootDuration,this.startTime=d):f>=e&&(this.state=g.done))):c===g.snapback&&(f>=e?(this.pos=this.toPos,this.state=g.done):this.pos=this.fromPos+(this.toPos-this.fromPos)*a.easing[this.easing](f/e,f,0,1,e)),this.pos)},done:function(){return this.state===g.done},isMin:function(){return this.pos===this.minPos},isMax:function(){return this.pos===this.maxPos},isAvail:function(){return this.minPos!==this.maxPos},getRemained:function(){return this.remained},getPosition:function(){return this.pos}}),a(c).bind("pagecreate create",function(b){var c=a(b.target),e=c.find(".ui-content").jqmData("scroll");a.support.scrollview===d&&(a.support.scrollview=!0),a.support.scrollview===!0&&e===d&&(e="y"),e!=="y"&&(e="none"),c.find(".ui-content").attr("data-scroll",e),c.find(":jqmData(scroll)").not(".ui-scrollview-clip").each(function(){if(a(this).hasClass("ui-scrolllistview"))a(this).scrolllistview();else{var b=a(this).jqmData("scroll"),c=b&&b.search(/^[xy]/)!==-1?b:null,e=a(this).hasClass("ui-content"),f;if(b==="none")return;f={direction:c||d,overflowEnable:e,scrollMethod:a(this).jqmData("scroll-method")||d,scrollJump:a(this).jqmData("scroll-jump")||d},a(this).scrollview(f)}})}),a(c).bind("pageshow",function(b){var c=a(b.target),d=c.find(".ui-content").jqmData("scroll");d==="y"&&e(b.target)})}(jQuery,window,document),ensureNS("jQuery.mobile.tizen.clrlib"),jQuery.extend(jQuery.mobile.tizen.clrlib,{nearestInt:function(a){var b=Math.floor(a);return a-b>.5?b+1:b},HTMLToRGB:function(a){return a="#"==a.charAt(0)?a.substring(1):a,[a.substring(0,2),a.substring(2,4),a.substring(4,6)].map(function(a){return parseInt(a,16)/255})},RGBToHTML:function(a){return"#"+a.map(function(a){var b=a*255,c=Math.floor(b);return b=b-c>.5?c+1:c,b=(b<16?"0":"")+(b&255).toString(16),b}).join("")},HSLToRGB:function(a){var b=a[0]/360,c=a[1],d=a[2];if(0===c)return[d,d,d];var e=d<.5?d*(1+c):d+c-d*c,f=2*d-e,g={r:b+1/3,g:b,b:b-1/3};return g.r=g.r<0?g.r+1:g.r>1?g.r-1:g.r,g.g=g.g<0?g.g+1:g.g>1?g.g-1:g.g,g.b=g.b<0?g.b+1:g.b>1?g.b-1:g.b,ret=[6*g.r<1?f+(e-f)*6*g.r:2*g.r<1?e:3*g.r<2?f+(e-f)*(2/3-g.r)*6:f,6*g.g<1?f+(e-f)*6*g.g:2*g.g<1?e:3*g.g<2?f+(e-f)*(2/3-g.g)*6:f,6*g.b<1?f+(e-f)*6*g.b:2*g.b<1?e:3*g.b<2?f+(e-f)*(2/3-g.b)*6:f],ret},HSVToRGB:function(a){return $.mobile.tizen.clrlib.HSLToRGB($.mobile.tizen.clrlib.HSVToHSL(a))},RGBToHSV:function(a){var b,c,d,e,f,g,h=a[0],i=a[1],j=a[2];return b=Math.min(h,Math.min(i,j)),c=Math.max(h,Math.max(i,j)),d=c-b,e=0,f=0,g=c,d>1e-5&&(f=d/c,h===c?e=(i-j)/d:i===c?e=2+(j-h)/d:e=4+(h-i)/d,e*=60,e<0&&(e+=360)),[e,f,g]},HSVToHSL:function(a){var b=a[2],c=a[1]*b,d=b-c,e=b+d,f=e/2,g=f<.5?e:2-b-d;return[a[0],0==g?0:c/g,f]},RGBToHSL:function(a){return $.mobile.tizen.clrlib.HSVToHSL($.mobile.tizen.clrlib.RGBToHSV(a))}}),function(a,b,c){pinch_event={setup:function(){function f(a){var b=a[0].x-a[1].x,c=a[0].y-a[1].y;return Math.abs(b*c)}function g(a,b){return{point:a,ratio:b}}var d=this,e=a(d);if(!a.mobile.support.touch)return;e.bind("touchstart",function(d){function l(c){var d=c.originalEvent.touches,e,h,l,m=a(b).width()/a.mobile.pinch.factor;if(k)return;if(!i)return;e=[{x:d[0].pageX,y:d[0].pageY},{x:d[1].pageX,y:d[1].pageY}],l=Math.sqrt(f(e)/f(i)),l&&(h=l),h<a.mobile.pinch.min?h=a.mobile.pinch.min:h>a.mobile.pinch.max&&(h=a.mobile.pinch.max);if(Math.abs(h-j)<a.mobile.pinch.threshold)return;a(c.target).trigger("pinch",g(e,h)),j=h,a.mobile.pinch.interval&&(k=!0,setTimeout(function(){k=!1},a.mobile.pinch.interval))}var h=d.originalEvent.touches,i,j=1,k=!1;if(!a.mobile.pinch.enabled)return;if(h.length!=2)return;i=[{x:h[0].pageX,y:h[0].pageY},{x:h[1].pageX,y:h[1].pageY}],a(d.target).trigger("pinchstart",g(i,c)),e.bind("touchmove",l).one("touchend",function(b){e.unbind("touchmove",l),a(b.target).trigger("pinchend",g(c,j)),i=c,current=c,j=1,k=!1})})}},a.event.special.pinch=pinch_event,a.mobile.pinch={enabled:!0,min:.1,max:3,factor:4,threshold:.01,interval:50}}(jQuery,this),function(a,b,c,d){a.widget("tizen.splitview",a.mobile.widget,{options:{fixed:!1,dividerVertical:!0,ratio:[],initSelector:":jqmData(role='splitview')"},_create:function(){var c=this,d=c.element,e=c.options,f=d.children(".ui-pane"),g=f.length,h=[],i=[],j=this.element.attr("data-ratio"),k=[0,0],l=null,m=0;if(g!==2){if(g<2)for(m=g;m<2;++m)c._addEmptyPanes();else f.slice(2).remove();f=d.children(".ui-pane"),g=f.length}h[0]=a("<a href='#' class='ui-spliter' aria-label='Drag scroll, double tap and move to adjust split area'></a>").insertAfter(f[0]),i[0]=a("<div class='ui-spliter-bar'></div>").appendTo(h[0]),a("<div class='ui-spliter-handle'></div>").appendTo(i[0]),a.extend(this,{moveTarget:null,moveData:{},spliters:h,spliterBars:i,panes:f,containerSize:k,touchStatus:!1,minPaneWidth:50,savedRatio:[]}),c._bindTouchEvents(),c._convertRatio(j,f.length),d.addClass("ui-splitview ui-direction-"+c._direction(e.dividerVertical)),c._refresh(),a(b).unbind(".splitview").bind("pagechange.splitview resize.splitview",function(b){a(".ui-page-active .ui-splitview").each(function(){a(this).data("splitview")._refresh()})})},_addEmptyPanes:function(){var b=this,c=b.element,d=b.options,e=c.children(".ui-pane"),f=a.support.scrollview?"data-scroll='y'":"",g=a("<div class='ui-pane' "+f+"></div>");f.length&&g.scrollview({direction:"y"}),e.length?e.last().after(g):c.append(g)},_direction:function(a){return a?"horizontal":"vertical"},_isStyleSpecified:function(a){return typeof a!="undefined"&&a.length},_getContainerSize:function(a,b){var c=this,d=c.element,e=c._isStyleSpecified(a),f=c._isStyleSpecified(b);return c.containerSize[0]=e?d.outerWidth(!0):c._parentWidth(),c.containerSize[1]=f?d.outerHeight(!0):c._parentHeight(),!c.containerSize[0]||!c.containerSize[1]?!1:!0},_parentWidth:function(){var c=this.element.parent();return!c&&typeof c=="undefined"&&!c.length?a(b).width():c.width()},_parentHeight:function(){var c=this.element.parent(),d="",e=!1,f=0;while(c&&typeof c!="undefined"&&c.length){if(typeof c[0].style!="undefined"){d=c[0].style.height,e=typeof d!="undefined"&&d.length;if(e){f=c.height();break}}c=c.parent()}return e||(f=a(b).height()),f},_convertRatio:function(b,c){var d=this,e=[],f=0,g=typeof b,h=null,i;for(i=0;i<c;++i)e.push(0);switch(g){case"number":c&&(e[0]=b);break;case"string":h=b.split(","),f=Math.min(h.length,c);for(i=0;i<f;++i)e[i]=parseFloat(h[i]);break;case"object":if(!a.isArray(b))break;f=Math.min(b.length,c);for(i=0;i<f;++i)g=typeof b[i],e[i]=g==="string"?parseFloat(b[i]):g==="number"?b[i]:0}d.options.ratio=e,d._adjustRatio(c)},_adjustRatio:function(a){var b=this,c=b.options.ratio,d=0,e=0,f=0,g=0,h=0,i;if(!a){b.options.ratio=[];return}for(i in c)d+=c[i];if(d!==1){e=1-d,f=e/a;for(i in c)f>=0?(c[i]+=f,e=Math.max(0,e-f)):(h+=f,g=Math.max(h,c[i]*-1),c[i]=Math.max(0,c[i]+g),e=Math.min(0,e-g),h-=g);if(e)if(e>0)c[c.length-1]+=e;else for(i=c.length-1;i>=0;--i){g=Math.max(e,c[i]*-1),c[i]=Math.max(0,c[i]+g),e=Math.min(0,e-g);if(!e)break}b.options.ratio=c}},_setOption:function(b,c){var d=this,e=d.options[b];if(e===c)return;a.Widget.prototype._setOption.apply(this,arguments);switch(b){case"fixed":d._fixed(c);break;case"dividerVertical":d._dividerVertical(c);break;case"ratio":d._ratio(c)}},_subtractDiffWidth:function(a,b){var c=this;return a<=c.minPaneWidth?{width:a,diff:b}:(a+=b,a>=c.minPaneWidth?{width:a,diff:0}:{width:c.minPaneWidth,diff:a-c.minPaneWidth})},_initRatio:function(b,c,d,e){var f=this,g=0,h=[],i=0,j=c.length,k,l;c.each(function(b){var c=a(this);h.push(d?c.width():c.height()),g+=h[b]}),i=e-g;if(!i)return h;if(i>0)h[b?0:j-1]+=i;else if(b)for(l=0;l<j;++l){k=f._subtractDiffWidth(h[l],i),h[l]=k.width,i=k.diff;if(!i)break}else for(l=j-1;l>=0;--l){i=f._subtractDiffWidth(h[l],i),h[l]=k.width,i=k.diff;if(!i)break}g=0;for(l in h)g+=h[l];for(l in f.options.ratio)f.options.ratio[l]=h[l]/g;return h},_horizontalBoundary:function(){var a=this,b=a.element;return b.outerWidth(!0)-b.width()},_verticalBoundary:function(){var a=this,b=a.element;return b.outerHeight(!0)-b.height()},_boundary:function(a){var c=this,d=c.element,e=b.getComputedStyle(d[0],null),f=parseFloat(e["margin"+a]),g=parseFloat(e["border"+a+"Width"]),h=parseFloat(e["padding"+a]);return{margin:f,border:g,padding:h}},_layout:function(b,c){var d=this,e=d.element,f=d.options,g=f.dividerVertical,h=d.panes,i=d.spliters,j=d.spliterBars,k=d.spliterBars.length?a(j[0]):null,l=k?g?k.outerWidth():k.outerHeight():0,m=k?g?k.outerWidth(!0)-k.outerWidth():k.outerHeight(!0)-k.outerHeight():0,n=h.length,o=0,p=l*(n-1),q=d.containerSize[0],r=d.containerSize[1],s=q-d._horizontalBoundary(),t=r-d._verticalBoundary(),u=g?t:s,v=g?s-p:t-p,w=[],x=0,y=null;b=!!b,c=!!c,e.css({"min-width":s,"min-height":t}),b&&(w=d._initRatio(c,h,g,v)),o=v,h.each(function(c){var e=a(this),f=b?w[c]:Math.floor(v*d.options.ratio[c]),i=c?h.eq(c-1):null,j=0,k=0,m=0,p=0;o-=f,c===n-1&&(f=Math.max(Math.min(f,d.minPaneWidth),f+o)),x+=f,i?(j=parseInt(i.css(g?"left":"top"),10),j+=g?i.width():i.height(),j+=l):(p=d._boundary(g?"Left":"Top"),j=p.padding),k=g?f:u,m=g?u:f,e.css({width:k,height:m}),e.css(g?"left":"top",j)}),h.each(function(b){var c=a(this),e=g?c.width():c.height();d.options.ratio[b]=e/x}),a.each(i,function(b){var c=a(this),d=h.eq(b),e=c.children(".ui-spliter-bar"),f=e.children(".ui-spliter-handle"),i=0;g?(i=parseInt(d.css("left"),10)+d.width()-m,c.outerHeight(u).css("left",i)):(i=parseInt(d.css("top"),10)+d.height()-m,c.outerWidth(u).css("top",i)),e.length&&e[g?"outerHeight":"outerWidth"](u),f.length&&f.css(g?"top":"left",(u-l)/2)}),y=e.find(".ui-splitview:first");if(!y.length)return;y=y.data("splitview"),y&&y._refresh()},_bindTouchEvents:function(){var b=this,c=b.element,d=b.panes,e=b.spliters;a.each(e,function(c){var d=a(this);b._bindSpliterTouchEvents.call(b,d)})},_bindSpliterTouchEvents:function(b){var d=this,e=d.element,f=d.options,g=a.support.touch?"touchstart":"mousedown",h=(a.support.touch?"touchmove":"mousemove")+".splitview",i=(a.support.touch?"touchend":"mouseup")+".splitview";b.bind(g,{e:b},function(b){if(d.options.fixed)return;var g=a.support.touch?b.originalEvent.changedTouches[0]:b,j=b.data.e,k=j.prev(),l=j.next(),m=k.find(".ui-splitview:first"),n=l.find(".ui-splitview:first"),o=f.dividerVertical,p=o?a(d.spliterBars[0]).outerWidth():a(d.spliterBars[0]).outerHeight();d.moveTarget=j,d.moveData={spliterWidth:p||0,prevPane:k,nextPane:l,splitviewInPrev:m,splitviewInNext:n,prevPanePos:parseInt(k.css(o?"left":"top"),10)||0,prevPaneWidth:parseInt(k.css(o?"width":"height"),10)||0,nextPanePos:parseInt(l.css(o?"left":"top"),10)||0,nextPaneWidth:parseInt(l.css(o?"width":"height"),10)||0,targetPos:parseInt(j.css(o?"left":"top"),10)||0,pagePos:o?g.pageX:g.pageY},j.addClass("ui-spliter-active"),e.bind(h,function(b){if(!d.touchStatus)return;b.stopPropagation(),d._drag(a.support.touch?b.originalEvent.changedTouches[0]:b)}).bind(i,function(b){b.stopPropagation(),d._stop(a.support.touch?b.originalEvent.changedTouches[0]:b),d.touchStatus=!1,e.unbind(".splitview"),a(c).unbind(".splitview")}),a(c).bind(h+" "+i,function(){e.trigger(i)}),b.preventDefault(),d.touchStatus=!0})},_drag:function(a){if(!this.moveData||typeof this.moveData=="undefined")return;var b=this,c=b.element,d=b.options,e=d.dividerVertical,f=b.moveData,g=b.moveTarget,h=f.prevPane,i=f.nextPane,j=f.splitviewInPrev,k=f.splitviewInNext,l=f.spliterWidth,m=null,n=null,o=null,p=null,q=null,r=e?a.pageX:a.pageY,s=null;m=r-f.pagePos,m>0?m=Math.min(Math.max(f.nextPaneWidth-b.minPaneWidth,0),m):m=Math.max(Math.max(f.prevPaneWidth-b.minPaneWidth,0)*-1,m),o=f.nextPanePos+m,p=Math.max(f.prevPaneWidth+m,0),q=Math.max(f.nextPaneWidth-m,0),n=f.targetPos+m,g.css(e?{left:n}:{top:n}),h.css(e?{width:p}:{height:p}),i.css(e?{width:q,left:o}:{height:q,top:o}),j.length&&(s=j.data("splitview"),s._refresh(!0,!1)),k.length&&(s=k.data("splitview"),s._refresh(!0,!0))},_stop:function(b){if(!this.moveData||!this.moveTarget)return;var c=this,d=c.element,e=c.options,f=c.panes,g=f.length,h=e.dividerVertical,i=c.moveData,j=c.moveTarget,k=i.prevPane,l=i.nextPane,m=i.splitviewInPrev,n=i.splitviewInNext,o=i.spliterWidth,p=o*(g-1),q=null,r=null,s=null,t=null,u=null,v=d.css("display"),w=c.containerSize[0],x=c.containerSize[1],y=w-c._horizontalBoundary(),z=x-c._verticalBoundary(),A=h?y-p:z-p,B=0;j.removeClass("ui-spliter-active"),f.each(function(b){var c=a(this),d=h?c.width():c.height();B+=d}),f.each(function(b){var d=a(this),e=h?d.width():d.height();c.options.ratio[b]=e/B}),c.moveData=null},_fixed:function(b){var c=this,d=c.spliters;a.each(d,function(c){var d=a(this);b?d.addClass("ui-fixed"):d.removeClass("ui-fixed")}),c._layout()},_dividerVertical:function(a){var b=this,c=b.element,d=a,e=null,f=null,g=null,h=null;e=c.children(".ui-pane"),f=c.children(".ui-spliter"),g=f.children(".ui-spliter-bar"),h=g.children(".ui-spliter-handle"),c.removeClass("ui-direction-vertical"),c.removeClass("ui-direction-horizontal"),c.addClass("ui-splitview ui-direction-"+b._direction(d)),e.css({left:"",top:"",width:"",height:""}),f.css({left:"",top:"",width:"",height:""}),g.css({width:"",height:""}),h.css({left:"",top:""}),b._getContainerSize(c[0].style.width,c[0].style.height)&&b._layout()},_ratio:function(a){var b=this,c=b.element,d=c.children(".ui-pane"),e=d.length;b._convertRatio(a,e),b._layout()},_refresh:function(a,b){var c=this,d=c.element;a=!!a,b=!!b,c._getContainerSize(d[0].style.width,d[0].style.height)&&c._layout(a,b)},pane:function(a,b){if(typeof a!="string")return null;var c=this,d=c.element,e=d.children(a),f=null,g=null;if(!e.hasClass("ui-pane"))return null;if(!b)return e.contents();if(e.hasClass("ui-scrollview-clip")){e.scrollview("scrollTo",0,0,0),f=e.children(".ui-scrollview-view");if(!f.length)return null}else f=e;g=b.parent();if(g.length&&g[0]===f[0])return;f.empty().append(b).trigger("create"),f.fadeIn("fast")},maximize:function(a){if(typeof a!="string")return;var b=this,c=b.element,d=b.panes,e=c.children(a);if(!e.hasClass("ui-pane"))return;b.savedRatio=b.options.ratio.slice(),b.options.ratio=[],d.each(function(a){b.options.ratio.push(this===e[0]?1:0)}),b._layout()},restore:function(){var a=this;if(!a.savedRatio.length)return;a.options.ratio=a.savedRatio.slice(),a._adjustRatio(a.panes.length),a._layout()}}),a(c).bind("pagecreate create",function(b){a.tizen.splitview.prototype.enhanceWithin(b.target)})}(jQuery,window,document),function(a,b,c){a.mobile.defaultPageTransition="none",a.mobile.transitionHandlers.depth=a.mobile.transitionHandlers
+.simultaneous,a.mobile.transitionFallbacks.depth="fade",a.fn.buttonMarkup.defaults.corners=!1,a.mobile.buttonMarkup.hoverDelay=0}(jQuery,this),function(a,b){var c={};a.widget("tizen.extendablelist",a.mobile.widget,{options:{theme:"s",countTheme:"c",headerTheme:"b",dividerTheme:"b",splitIcon:"arrow-r",splitTheme:"b",inset:!1,id:"",extenditems:50,childSelector:" li",dbtable:"",template:"",loadmore:"tmp_load_more",scrollview:!1,initSelector:":jqmData(role='extendablelist')"},_stylerMouseUp:function(){a(this).addClass("ui-btn-up-s"),a(this).removeClass("ui-btn-down-s")},_stylerMouseDown:function(){a(this).addClass("ui-btn-down-s"),a(this).removeClass("ui-btn-up-s")},_stylerMouseOver:function(){a(this).toggleClass("ui-btn-hover-s")},_stylerMouseOut:function(){a(this).toggleClass("ui-btn-hover-s"),a(this).addClass("ui-btn-up-s"),a(this).removeClass("ui-btn-down-s")},_pushData:function(b){var c=this.options,d=this,e=0,f=a("#"+b),g=c.extenditems>d._numItemData-d._lastIndex?d._numItemData-d.lastIndex:c.extenditems,h;for(e=0;e<g;e++)h=f.tmpl(d._itemData(e)),a(c.id).append(a(h).attr("id","li_"+e)),a(c.id+">"+c.childSelector).addClass("ui-btn-up-s").bind("mouseup",d._stylerMouseUp).bind("mousedown",d._stylerMouseDown).bind("mouseover",d._stylerMouseOver).bind("mouseout",d._stylerMouseOut),d._lastIndex+=1;a(c.id).trigger("create")},_loadmore:function(b){var c=b.data,d=c.options,e=0,f=a("#"+d.template),g=d.extenditems>c._numItemData-c._lastIndex?c._numItemData-c._lastIndex:d.extenditems,h,i,j;a("#load_more_message").remove();for(e=0;e<g;e++)h=f.tmpl(c._itemData(c._lastIndex)),a(d.id).append(a(h).attr("id","li_"+c._lastIndex)),c._lastIndex+=1;c._numItemData>c._lastIndex&&(f=a("#"+d.loadmore),i=c._numItemData-c._lastIndex,j=d.extenditems<=i?d.extenditems:i,h=f.tmpl({NUM_MORE_ITEMS:j}),a(d.id).append(a(h).attr("id","load_more_message").css("min-height","37px"))),a(d.id).trigger("create"),a(d.id).extendablelist("refresh")},recreate:function(a){this._create({itemData:function(b){return a[b]},numItemData:a.length})},_initList:function(b){var c=this,d=this.options,e,f,g,h;c._lastIndex<=0&&(c._pushData(d.template),c._numItemData>c._lastIndex?(e=a("#"+d.loadmore),f=c._numItemData-c._lastIndex,g=d.extenditems<=f?d.extenditems:f,h=e.tmpl({NUM_MORE_ITEMS:g}),a(d.id).append(a(h).attr("id","load_more_message").css("min-height","37px")),a("#load_more_message").live("click",c,c._loadmore)):(a("#load_more_message").die(),a("#load_more_message").remove())),d.childSelector==" ul"&&a(d.id+" ul").swipelist(),a(d.id).trigger("create"),c.refresh(!0)},create:function(){var a=this.options;this._create.apply(this,arguments)},_create:function(b){var c=this,d=this.options,e=this.element,f;c.destroy(),a.extend(this,{_itemData:function(a){return null},_numItemData:0,_cacheItemData:function(a,b){},_lastIndex:0}),c.element.addClass(function(a,b){return b+" ui-listview ui-extendable-list-container"+(c.options.inset?" ui-listview-inset ui-corner-all ui-shadow ":"")}),d.id="#"+e.attr("id"),e.data("extenditems")&&(d.extenditems=parseInt(e.data("extenditems"),10)),a(d.id).bind("pagehide",function(b){a(d.id).empty()}),a(".ui-scrollview-clip").size()>0?d.scrollview=!0:d.scrollview=!1;if(b){if(!c._loadData(b))return}else{console.warn("WARNING: The data interface of extendable list is changed. \nOld data interface(data-dbtable) is still supported, but will be removed in next version. \nPlease fix your code soon!");if(!a(d.id).hasClass("elLoadSuccess")){console.warn("No elLoadSuccess class");return}f=e.jqmData("dbtable"),d.dbtable=window[f],d.dbtable||(d.dbtable={}),c._itemData=function(a){return d.dbtable[a]},c._numItemData=d.dbtable.length}e.data("template")&&(d.template=e.data("template"),e.data("swipelist")==1?d.childSelector=" ul":d.shildSelector=" li"),c._initList(b)},_loadData:function(a){var b=this;if(!a.itemData||typeof a.itemData!="function")return!1;b._itemData=a.itemData;if(!a.numItemData)return!1;if(typeof a.numItemData=="function")b._numItemData=a.numItemData();else{if(typeof a.numItemData!="number")return!1;b._numItemData=a.numItemData}return!0},destroy:function(){var b=this.options,c=0,d=0;a(b.id).empty(),a("#load_more_message").die()},_itemApply:function(b,c){var d=c.find(".ui-li-count");d.length&&c.addClass("ui-li-has-count"),d.addClass("ui-btn-up-"+(b.jqmData("counttheme")||this.options.countTheme)+" ui-btn-corner-all"),c.find("h1, h2, h3, h4, h5, h6").addClass("ui-li-heading").end().find("p, dl").addClass("ui-li-desc").end().find(">img:eq(0), .ui-link-inherit>img:eq(0)").addClass("ui-li-thumb").each(function(){c.addClass(a(this).is(".ui-li-icon")?"ui-li-has-icon":"ui-li-has-thumb")}).end().find(".ui-li-aside").each(function(){var b=a(this);b.prependTo(b.parent())})},_removeCorners:function(a,b){var c="ui-corner-top ui-corner-tr ui-corner-tl",d="ui-corner-bottom ui-corner-br ui-corner-bl";a=a.add(a.find(".ui-btn-inner, .ui-li-link-alt, .ui-li-thumb")),b==="top"?a.removeClass(c):b==="bottom"?a.removeClass(d):a.removeClass(c+" "+d)},_refreshCorners:function(a){var b,c,d,e;this.options.inset&&(b=this.element.children("li"),c=a?b.not(".ui-screen-hidden"):b.filter(":visible"),this._removeCorners(b),d=c.first().addClass("ui-corner-top"),d.add(d.find(".ui-btn-inner")).find(".ui-li-link-alt").addClass("ui-corner-tr").end().find(".ui-li-thumb").not(".ui-li-icon").addClass("ui-corner-tl"),e=c.last().addClass("ui-corner-bottom"),e.add(e.find(".ui-btn-inner")).find(".ui-li-link-alt").addClass("ui-corner-br").end().find(".ui-li-thumb").not(".ui-li-icon").addClass("ui-corner-bl"))},refresh:function(b){this.parentPage=this.element.closest(".ui-page"),this._createSubPages();var c=this.options,d=this.element,e=this,f=d.jqmData("dividertheme")||c.dividerTheme,g=d.jqmData("splittheme"),h=d.jqmData("spliticon"),i=d.children("li"),j=a.support.cssPseudoElement||!a.nodeName(d[0],"ol")?0:1,k,l,m,n,o,p,q,r,s,t;j&&d.find(".ui-li-dec").remove();for(s=0,t=i.length;s<t;s++){k=i.eq(s),l="ui-li";if(b||!k.hasClass("ui-li"))m=k.jqmData("theme")||c.theme,n=k.children("a"),n.length?(r=k.jqmData("icon"),k.buttonMarkup({wrapperEls:"div",shadow:!1,corners:!1,iconpos:"right",icon:!1,theme:m}),r!=0&&n.length==1&&k.addClass("ui-li-has-arrow"),n.first().addClass("ui-link-inherit"),n.length>1&&(l+=" ui-li-has-alt",o=n.last(),p=g||o.jqmData("theme")||c.splitTheme,o.appendTo(k).attr("title",o.getEncodedText()).addClass("ui-li-link-alt").empty().buttonMarkup({shadow:!1,corners:!1,theme:m,icon:!1,iconpos:!1}).find(".ui-btn-inner").append(a("<span />").buttonMarkup({shadow:!0,corners:!0,theme:p,iconpos:"notext",icon:h||o.jqmData("icon")||c.splitIcon})))):k.jqmData("role")==="list-divider"?(l+=" ui-li-divider ui-btn ui-bar-"+f,k.attr("role","heading"),j&&(j=1)):l+=" ui-li-static ui-body-"+m;j&&l.indexOf("ui-li-divider")<0&&(q=k.is(".ui-li-static:first")?k:k.find(".ui-link-inherit"),q.addClass("ui-li-jsnumbering").prepend("<span class='ui-li-dec'>"+j++ +". </span>")),k.add(k.children(".ui-btn-inner")).addClass(l),e._itemApply(d,k)}this._refreshCorners(b)},_idStringEscape:function(a){return a.replace(/\W/g,"-")},_createSubPages:function(){var b=this.element,d=b.closest(".ui-page"),e=d.jqmData("url"),f=e||d[0][a.expando],g=b.attr("id"),h=this.options,i="data-"+a.mobile.ns,j=this,k=d.find(":jqmData(role='footer')").jqmData("id"),l,m;typeof c[f]=="undefined"&&(c[f]=-1),g=g||++c[f],a(b.find("li>ul, li>ol").toArray().reverse()).each(function(c){var d=this,f=a(this),j=f.attr("id")||g+"-"+c,m=f.parent(),n,p=n.first().getEncodedText(),q=(e||"")+"&"+a.mobile.subPageUrlKey+"="+j,r=f.jqmData("theme")||h.theme,s=f.jqmData("counttheme")||b.jqmData("counttheme")||h.countTheme,t,u;n=a(f.prevAll().toArray().reverse()),n=n.length?n:a("<span>"+a.trim(m.contents()[0].nodeValue)+"</span>"),l=!0,t=f.detach().wrap("<div "+i+"role='page' "+i+"url='"+q+"' "+i+"theme='"+r+"' "+i+"count-theme='"+s+"'><div "+i+"role='content'></div></div>").parent().before("<div "+i+"role='header' "+i+"theme='"+h.headerTheme+"'><div class='ui-title'>"+p+"</div></div>").after(k?a("<div "+i+"role='footer' "+i+"id='"+k+"'>"):"").parent().appendTo(a.mobile.pageContainer),t.page(),u=m.find("a:first"),u.length||(u=a("<a/>").html(n||p).prependTo(m.empty())),u.attr("href","#"+q)}).extendablelist(),l&&d.is(":jqmData(external-page='true')")&&d.data("page").options.domCache===!1&&(m=function(b,c){var f=c.nextPage,g;c.nextPage&&(g=f.jqmData("url"),g.indexOf(e+"&"+a.mobile.subPageUrlKey)!==0&&(j.childPages().remove(),d.remove()))},d.unbind("pagehide.remove").bind("pagehide.remove",m))},childPages:function(){var b=this.parentPage.jqmData("url");return a(":jqmData(url^='"+b+"&"+a.mobile.subPageUrlKey+"')")}}),a(document).bind("pagecreate create",function(b){a(a.tizen.extendablelist.prototype.options.initSelector,b.target).extendablelist()})}(jQuery),function(a,b){a.widget("tizen.fastscroll",a.mobile.widget,{options:{initSelector:":jqmData(fastscroll)"},_primaryLanguage:null,_secondLanguage:null,_dividerMap:{},_defaultTime:500,_defaultDuration:500,_timer:null,_isFadeOut:!1,_create:function(){var b=this.element,c=this,d,e=b.closest(':jqmData(role="page")'),f;this.scrollview=b.addClass("ui-fastscroll-target").closest(".ui-scrollview-clip"),this.shortcutsContainer=a('<div class="ui-fastscroll" aria-label="Fast scroll bar, double tap to fast scroll mode" tabindex="0"/>'),this.shortcutsList=a('<ul aria-hidden="true"></ul>'),this.scrollview.append(a('<div class="ui-fastscroll-popup"></div>')),d=this.scrollview.find(".ui-fastscroll-popup"),this.shortcutsContainer.append(this.shortcutsList),this.scrollview.append(this.shortcutsContainer),this.lastListItem=b.children().last(),this.scrollview.find(".ui-scrollbar").hide(),this.jumpToDivider=function(b){var d=a(b).position().top,e=c.lastListItem.outerHeight(!0)+c.lastListItem.position().top,f=c.scrollview.height(),g=e-f,h;d=d>g?g:d,d=Math.max(d,0),c.scrollview.scrollview("scrollTo",0,-d),h=c.scrollview.offset()},this.shortcutsList.bind("touchstart mousedown vmousedown touchmove vmousemove vmouseover",function(b){var d=a.mobile.tizen.targetRelativeCoordsFromEvent(b),e=c.shortcutsList.offset();if(c._isFadeOut===!0)return;b.target.tagName.toLowerCase()==="li"&&(d.x+=a(b.target).offset().left-e.left,d.y+=a(b.target).offset().top-e.top),b.target.tagName.toLowerCase()==="span"&&(d.x+=a(b.target).parent().offset().left-e.left,d.y+=a(b.target).parent().offset().top-e.top),c.shortcutsList.find("li").each(function(){var b=a(this);a(b).removeClass("ui-fastscroll-hover").removeClass("ui-fastscroll-hover-down")}),c.shortcutsList.find("li").each(function(){var b=a(this),f=b.offset().left-e.left,g=b.offset().top-e.top,h=f+Math.abs(b.outerWidth(!0)),i=g+Math.abs(b.outerHeight(!0)),j,k,l,m,n;if(d.x>=f&&d.x<=h&&d.y>=g&&d.y<=i){if(b.text()!==".")c._hitItem(b);else{m=b.data("omitSet"),j=(i-g)/m.length;for(n=0;n<m.length;n++)k=g+n*j,l=k+j,d.y>=k&&d.y<=l&&c._hitOmitItem(b,m.charAt(n))}return!1}return!0}),c._setTimer(!1),b.preventDefault(),b.stopPropagation()}).bind("touchend mouseup vmouseup vmouseout",function(){d.hide(),a(".ui-fastscroll-hover").removeClass("ui-fastscroll-hover"),a(".ui-fastscroll-hover-first-item").removeClass("ui-fastscroll-hover-first-item"),a(".ui-fastscroll-hover-down").removeClass("ui-fastscroll-hover-down"),c._setTimer(!0)}),e&&!e.is(":visible")?e.bind("pageshow",function(){c.refresh()}):c.refresh(),b.bind("updatelayout",function(){c.refresh()}),c.scrollview.bind("scrollstart",function(a){c._setTimer(!1)}).bind("scrollstop",function(a){c._setTimer(!0)})},_hitOmitItem:function(b,c){var d=this,e=d.scrollview.find(".ui-fastscroll-popup"),f=d._dividerMap[c];typeof f!="undefined"&&d.jumpToDivider(a(f)),e.text(c).css({marginLeft:-(e.outerWidth()/2),marginTop:-(e.outerHeight()/2),padding:e.css("paddingTop")}).width(e.height()).show(),a(b).addClass("ui-fastscroll-hover"),b.index()===0&&a(b).addClass("ui-fastscroll-hover-first-item"),a(b).siblings().eq(b.index()).addClass("ui-fastscroll-hover-down")},_hitItem:function(b){var c=this,d=c.scrollview.find(".ui-fastscroll-popup"),e=b.text(),f;e==="#"?f=c._dividerMap.number:f=c._dividerMap[e],typeof f!="undefined"&&c.jumpToDivider(a(f)),d.text(e).css({marginLeft:-(d.outerWidth()/2),marginTop:-(d.outerHeight()/2),padding:d.css("paddingTop")}).width(d.height()).show(),a(b).addClass("ui-fastscroll-hover"),b.index()===0&&a(b).addClass("ui-fastscroll-hover-first-item"),a(b).siblings().eq(b.index()).addClass("ui-fastscroll-hover-down")},_focusItem:function(b){var c=this,d=c.scrollview.find(".ui-fastscroll-popup");b.focusin(function(a){c.shortcutsList.attr("aria-hidden",!1),c._hitItem(b),c._setTimer(!1)}).focusout(function(b){c.shortcutsList.attr("aria-hidden",!0),d.hide(),a(".ui-fastscroll-hover").removeClass("ui-fastscroll-hover"),a(".ui-fastscroll-hover-first-item").removeClass("ui-fastscroll-hover-first-item"),a(".ui-fastscroll-hover-down").removeClass("ui-fastscroll-hover-down"),c._setTimer(!0)})},_contentHeight:function(){var b=this,c=a(".ui-scrollview-clip"),d=null,e=null,f=0,g=a(window).height();return c.hasClass("ui-content")?(f=parseInt(c.css("padding-top"),10),g-=f||0,f=parseInt(c.css("padding-bottom"),10),g-=f||0,d=c.siblings(".ui-header:visible"),e=c.siblings(".ui-footer:visible"),d&&(d.outerHeight(!0)===null?g-=a(".ui-header").outerHeight()||0:g-=d.outerHeight(!0)),e&&(g-=e.outerHeight(!0))):g=c.height(),g},_omit:function(a,b){var c=parseInt((b-1)/2,10),d=a-b,e=[],f=[],g,h,i,j;if(b<3||a<=b)return;d>=c?(i=2,h=1,g=c):(i=b/(d+1),h=i,g=d);for(j=0;j<g;j++)e.push(parseInt(h,10)),h+=i;for(j=0;j<b;j++)f.push(1);for(j=0;j<d;j++)f[e[j%c]]++;return f},_createDividerMap:function(){var b=this,c=b._primaryLanguage?b._primaryLanguage.replace(/,/g,""):null,d=b._secondLanguage?b._secondLanguage.replace(/,/g,""):null,e="0123456789",f=b.element.find(".ui-li-divider"),g={},h,i,j,k;h=function(b,c){a(c).text()===j&&(g[j]=c)},i=function(b,d){c+=a(d).text()},c===null&&(c="",f.each(i));for(k=0;k<c.length;k++)j=c.charAt(k),f.each(h);if(d!==null)for(k=0;k<d.length;k++)j=d.charAt(k),f.each(h);f.each(function(b,c){if(e.search(a(c).text())!==-1)return g.number=c,!1}),b._dividerMap=g},_setTimer:function(a){var b=this;a===!0?b._timer=setTimeout(function(){b._isFadeOut=!0,b.shortcutsContainer.fadeOut(b._defaultDuration,function(){b._isFadeOut=!1})},b._defaultTime):(b._timer!==null&&clearTimeout(b._timer),b.shortcutsContainer.show())},indexString:function(a){var b=this,c=[];if(typeof a=="undefined")return b._primaryLanguage+":"+b._secondLanguage;c=a.split(":"),b._primaryLanguage=c[0],c.length===2&&(b._secondLanguage=c[1])},refresh:function(){var b=this,c=b._primaryLanguage?b._primaryLanguage.replace(/,/g,""):null,d=b._secondLanguage?b._secondLanguage.replace(/,/g,""):null,e=b._contentHeight(),f=a('<li tabindex="0" aria-label="double to move Number list"><span aria-hidden="true">#</span><span aria-label="Number"/></li>'),g=0,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,A,B,C,D;h=function(b,d){c+=a(d).text()},i=function(a,b){var d,e="";for(d=0;d<b;d++)e+=c[a+d];return e},j=function(c){var d=a(this).text(),e=b._dividerMap[d];typeof e!="undefined"&&a(e).next().focus()},b._createDividerMap(),b.shortcutsList.find("li").remove(),u=b.element.find(".ui-li-divider"),v=b.element.find("li").not(".ui-li-divider"),u=u.filter(":visible"),v=v.filter(":visible");if(u.length<2){b.shortcutsList.hide();return}b.shortcutsList.show(),b.lastListItem=v.last(),b.shortcutsList.append(f),b._focusItem(f),c===null&&(c="",u.each(h)),s=parseInt(f.css("padding"),10),r=f.height()+s*2,p=parseInt(e/r-1,10),q=c.length,p=d?p-2:p;if(p<3){f.remove();return}t=b._omit(q,p);for(D=0;D<c.length;D++)y=c.charAt(D),m=a('<li tabindex="0" aria-label="double to move '+y+' list">'+y+"</li>"),b._focusItem(m),typeof t!="undefined"&&t[g]>1?(m=a("<li>.</li>"),m.data("omitSet",i(D,t[g])),D+=t[g]-1):m.bind("vclick",j),f.before(m),g++;if(d!==null){z=d.length-1,A=[],A.push(d.charAt(0)),A.push(d.charAt(z));for(D=0;D<A.length;D++)y=A[D],m=a('<li tabindex="0" aria-label="double to move '+y+' list">'+y+"</li>"),b._focusItem(m),m.bind("vclick",j),f.before(m)}k=b.shortcutsContainer.outerHeight(),w=e-k,l=b.shortcutsList.children(),C=parseInt(w/l.length,10),x=w-l.length*C,w>0&&l.each(function(b,c){B=a(c).height()+C,x!==0&&(B+=1,x-=1),a(c).css({height:B,lineHeight:B+"px"})}),n=u.first().position().top,b.shortcutsContainer.css("top",n),o=n+b.shortcutsContainer.outerHeight()+"px",b.scrollview.css("min-height",o),b._setTimer(!1),b._setTimer(!0)}}),a(document).bind("pagecreate create",function(b){a(a.tizen.fastscroll.prototype.options.initSelector,b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").fastscroll()}),a(window).bind("resize orientationchange",function(b){a(".ui-page-active .ui-fastscroll-target").fastscroll("refresh")})}(jQuery),function(a,b,c,d){function e(a,b){var c=a%b;return c<0&&(c=b+c),c}function f(a,b,c){var d="translate3d( "+b+","+c+", 0px)";a.css({"-ms-transform":d,"-o-transform":d,"-moz-transform":d,"-webkit-transform":d,transform:d})}function g(b){this.options=a.extend({},b),this.easing="easeOutQuad",this.reset()}function i(){return Date.now()}var h={scrolling:0,done:1};a.extend(g.prototype,{start:function(a,b,c){this.state=b!=0?h.scrolling:h.done,this.pos=a,this.speed=b,this.duration=c,this.fromPos=0,this.toPos=0,this.startTime=i()},reset:function(){this.state=h.done,this.pos=0,this.speed=0,this.duration=0},update:function(){var b=this.state,c,d,e,f;return b==h.done?this.pos:(c=this.duration,d=i()-this.startTime,d=d>c?c:d,e=this.speed*(1-a.easing[this.easing](d/c,d,0,1,c)),f=this.pos+e,this.pos=f,d>=c&&(this.state=h.done),this.pos)},done:function(){return this.state==h.done},getPosition:function(){return this.pos}}),jQuery.widget("mobile.circularview",jQuery.mobile.widget,{options:{fps:60,scrollDuration:2e3,moveThreshold:10,moveIntervalThreshold:150,startEventName:"scrollstart",updateEventName:"scrollupdate",stopEventName:"scrollstop",eventType:a.support.touch?"touch":"mouse",delayedClickSelector:"a, .ui-btn",delayedClickEnabled:!1},_makePositioned:function(a){a.css("position")=="static"&&a.css("position","relative")},_create:function(){var b=this;this._items=a(this.element).jqmData("list"),this._$clip=a(this.element).addClass("ui-scrollview-clip"),this._$clip.wrapInner('<div class="ui-scrollview-view"></div>'),this._$view=a(".ui-scrollview-view",this._$clip),this._$list=a("ul",this._$clip),this._$clip.css("overflow","hidden"),this._makePositioned(this._$clip),this._$view.css("overflow","hidden"),this._tracker=new g(this.options),this._timerInterval=1e3/this.options.fps,this._timerID=0,this._timerCB=function(){b._handleMomentumScroll()},this.refresh(),this._addBehaviors()},reflow:function(){var a=this.getScrollPosition();this.refresh(),this.scrollTo(a.x,a.y)},refresh:function(){var c;this._$clip.width(a(b).width()),this._clipWidth=this._$clip.width(),this._$list.empty(),this._$list.append(this._items[0]),this._itemWidth=a(this._items[0]).outerWidth(),a(this._items[0]).detach(),c=this._clipWidth/this._itemWidth,c=Math.ceil(c*10)/10,this._itemsPerView=parseInt(c,10);while(this._itemsPerView+1>this._items.length)a.merge(this._items,a(this._items).clone());this._rx=-this._itemWidth,this._sx=-this._itemWidth,this._setItems()},_startMScroll:function(a,b){this._stopMScroll();var c=!1,d=this.options.scrollDuration,e=this._tracker,f=this._clipWidth,g=this._viewWidth;this._$clip.trigger(this.options.startEventName),e.start(this._rx,a,d,g>f?-(g-f):0,0),c=!e.done(),c?this._timerID=setTimeout(this._timerCB,this._timerInterval):this._stopMScroll()},_stopMScroll:function(){this._timerID&&(this._$clip.trigger(this.options.stopEventName),clearTimeout(this._timerID)),this._timerID=0,this._tracker&&this._tracker.reset()},_handleMomentumScroll:function(){var a=!1,b=this._$view,c=0,d=0,e=this._tracker;e&&(e.update(),c=e.getPosition(),a=!e.done()),this._setScrollPosition(c,d),this._rx=c,this._$clip.trigger(this.options.updateEventName,[{x:c,y:d}]),a?this._timerID=setTimeout(this._timerCB,this._timerInterval):this._stopMScroll()},_setItems:function(){var a,b;for(a=-1;a<this._itemsPerView+1;a++)b=this._items[e(a,this._items.length)],this._$list.append(b);f(this._$view,this._sx+"px",0),this._$view.width(this._itemWidth*(this._itemsPerView+2)),this._viewWidth=this._$view.width()},_setScrollPosition:function(a,b){var c=this._sx,d=a-c,g=parseInt(d/this._itemWidth,10),h,i,j;if(g>0)for(h=0;h<g;h++)this._$list.children().last().detach(),i=-parseInt(c/this._itemWidth+h+3,10),j=this._items[e(i,this._items.length)],this._$list.prepend(j);else if(g<0)for(h=0;h>g;h--)this._$list.children().first().detach(),i=this._itemsPerView-parseInt(c/this._itemWidth+h,10),j=this._items[e(i,this._items.length)],this._$list.append(j);this._sx+=g*this._itemWidth,f(this._$view,a-this._sx-this._itemWidth+"px",0)},_enableTracking:function(){a(c).bind(this._dragMoveEvt,this._dragMoveCB),a(c).bind(this._dragStopEvt,this._dragStopCB)},_disableTracking:function(){a(c).unbind(this._dragMoveEvt,this._dragMoveCB),a(c).unbind(this._dragStopEvt,this._dragStopCB)},_getScrollHierarchy:function(){var b=[],c;return this._$clip.parents(".ui-scrollview-clip").each(function(){c=a(this).jqmData("circulaview"),c&&b.unshift(c)}),b},centerTo:function(b,c){var d,e;for(d=0;d<this._items.length;d++)if(a(this._items[d]).is(b)){e=-(d*this._itemWidth-this._clipWidth/2+this._itemWidth*1.5),this.scrollTo(e+this._itemWidth,0),this.scrollTo(e,0,c);return}},scrollTo:function(b,c,d){this._stopMScroll();if(!d){this._setScrollPosition(b,c),this._rx=b;return}var e=this,f=i(),g=a.easing.easeOutQuad,h=this._rx,j=0,k=b-h,l=0,m,n,o;this._rx=b,m=function(){n=i()-f,n>=d?(e._timerID=0,e._setScrollPosition(b,c),e._$clip.trigger("scrollend")):(o=g(n/d,n,0,1,d),e._setScrollPosition(h+k*o,j+l*o),e._timerID=setTimeout(m,e._timerInterval))},this._timerID=setTimeout(m,this._timerInterval)},getScrollPosition:function(){return{x:-this._rx,y:0}},_handleDragStart:function(b,c,d){a.each(this._getScrollHierarchy(),function(a,b){b._stopMScroll()}),this._stopMScroll(),this.options.delayedClickEnabled&&(this._$clickEle=a(b.target).closest(this.options.delayedClickSelector)),this._lastX=c,this._lastY=d,this._speedX=0,this._speedY=0,this._didDrag=!1,this._lastMove=0,this._enableTracking(),this._ox=c,this._nx=this._rx,(this.options.eventType=="mouse"||this.options.delayedClickEnabled)&&b.preventDefault(),b.stopPropagation()},_handleDragMove:function(a,b,c){this._lastMove=i();var d=b-this._lastX,e=c-this._lastY;return this._speedX=d,this._speedY=0,this._didDrag=!0,this._lastX=b,this._lastY=c,this._mx=b-this._ox,this._setScrollPosition(this._nx+this._mx,0),!1},_handleDragStop:function(a){var b=this._lastMove,c=i(),e=b&&c-b<=this.options.moveIntervalThreshold,f=this._tracker&&this._speedX&&e?this._speedX:0,g=0;return this._rx=this._mx?this._nx+this._mx:this._rx,f&&this._startMScroll(f,g),this._disableTracking(),!this._didDrag&&this.options.delayedClickEnabled&&this._$clickEle.length&&this._$clickEle.trigger("mousedown").trigger("mouseup").trigger("click"),this._didDrag&&(a.preventDefault(),a.stopPropagation()),this._didDrag?!1:d},_addBehaviors:function(){var a=this;this.options.eventType==="mouse"?(this._dragStartEvt="mousedown",this._dragStartCB=function(b){return a._handleDragStart(b,b.clientX,b.clientY)},this._dragMoveEvt="mousemove",this._dragMoveCB=function(b){return a._handleDragMove(b,b.clientX,b.clientY)},this._dragStopEvt="mouseup",this._dragStopCB=function(b){return a._handleDragStop(b)},this._$view.bind("vclick",function(b){return!a._didDrag})):(this._dragStartEvt="touchstart",this._dragStartCB=function(b){var c=b.originalEvent.targetTouches[0];return a._handleDragStart(b,c.pageX,c.pageY)},this._dragMoveEvt="touchmove",this._dragMoveCB=function(b){var c=b.originalEvent.targetTouches[0];return a._handleDragMove(b,c.pageX,c.pageY)},this._dragStopEvt="touchend",this._dragStopCB=function(b){return a._handleDragStop(b)}),this._$view.bind(this._dragStartEvt,this._dragStartCB)}}),a(c).bind("pagecreate create",function(b){a(a.mobile.circularview.prototype.options.initSelector,b.target).circularview()})}(jQuery,window,document),function(a,b,c,d){a.widget("tizen.multimediaview",a.mobile.widget,{options:{theme:null,controls:!0,fullScreen:!1,initSelector:"video, audio"},_create:function(){var b=this,c=b.element,d=c[0],e=d.nodeName==="VIDEO",f=b.options,g=a.mobile.getInheritedTheme(c,"s"),h=f.theme||g,i=d.style.getPropertyValue("width")||"",j=a("<div class='ui-multimediaview-wrap ui-multimediaview-"+h+"'>"),k=null;a.extend(this,{role:null,controlTimer:null,isVolumeHide:!0,backupView:null,_reserveVolume:-1,_isVideo:e}),c.addClass("ui-multimediaview"),k=b._createControl(),k.hide(),k.find(".ui-button").each(function(b){a(this).buttonMarkup({corners:!0,theme:h,shadow:!0})}),c.wrap(j).after(k),e?k.addClass("ui-multimediaview-video"):(b.width(i),b.options.fullScreen=!1),f.controls&&c.attr("controls")&&c.removeAttr("controls"),b._addEvent()},_resize:function(){this._resizeFullscreen(this.options.fullScreen),this._resizeControl(),this._updateSeekBar(),this._updateVolumeState()},_resizeControl:function(){var a=this,b=a.element,c=b[0],d=a._isVideo,e=b.parent(".ui-multimediaview-wrap"),f=e.find(".ui-multimediaview-control"),g=f.find(".ui-button"),h=f.find(".ui-playpausebutton"),i=f.find(".ui-seekbar"),j=f.find(".ui-durationlabel"),k=f.find(".ui-timestamplabel"),l=f.find(".ui-volumecontrol"),m=l.find(".ui-volumebar"),n=d?b.width():e.width(),o=d?b.height():f.height(),p=b.offset(),q=f.height(),r=0,s=null;f&&(d&&(s=f.offset(),s.left=p.left,s.top=p.top+o-q,f.offset(s)),f.width(n)),i&&(r=f.width()-g.outerWidth(!0)*g.length,r-=(parseInt(g.eq(0).css("margin-left"),10)+parseInt(g.eq(0).css("margin-right"),10))*g.length,a.isVolumeHide||(r-=l.outerWidth(!0)),i.width(r)),j&&!isNaN(c.duration)&&j.find("p").text(a._convertTimeFormat(c.duration)),c.autoplay&&c.paused===!1&&h.removeClass("ui-play-icon").addClass("ui-pause-icon"),i.width()<m.width()+k.width()+j.width()?j.hide():j.show()},_resizeFullscreen:function(b){if(!this._isVideo)return;var d=this,e=d.element,f=e[0],g=e.parent(".ui-multimediaview-wrap"),h=g.find(".ui-multimediaview-control"),i=h.find(".ui-fullscreenbutton"),j=a(".ui-page-active"),k=h.find(".ui-playpausebutton"),l=h.find(".ui-timestamplabel"),m=h.find(".ui-seekbar"),n=m.find(".ui-duration"),o=m.find(".ui-currenttime"),p=a("body")[0],q=j.children(".ui-header"),r=j.children(".ui-footer"),s=0,t=0;if(b)d.backupView||(d.backupView={width:f.style.getPropertyValue("width")||"",height:f.style.getPropertyValue("height")||"",position:e.css("position"),zindex:e.css("z-index"),wrapHeight:g[0].style.getPropertyValue("height")||""}),s=p.clientWidth,t=p.clientHeight-1,q.hide(),r.hide(),e.parents().each(function(b){var c=a(this);c.addClass("ui-fullscreen-parents").siblings().addClass("ui-multimediaview-siblings-off")}),i.removeClass("ui-fullscreen-on").addClass("ui-fullscreen-off"),g.height(t),e.width(s).height(t);else{if(!d.backupView)return;q.show(),r.show(),e.parents().each(function(b){var c=a(this);c.removeClass("ui-fullscreen-parents").siblings().removeClass("ui-multimediaview-siblings-off")}),i.removeClass("ui-fullscreen-off").addClass("ui-fullscreen-on"),g.css("height",d.backupView.wrapHeight),e.css({width:d.backupView.width,height:d.backupView.height,position:d.backupView.position,"z-index":d.backupView.zindex}),d.backupView=null,a(c).trigger("throttledresize")}},_addEvent:function(){var c=this,d=c.element,e=c.options,f=d[0],g=c._isVideo,h=d.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),i=h.find(".ui-playpausebutton"),j=h.find(".ui-timestamplabel"),k=h.find(".ui-durationlabel"),l=h.find(".ui-volumebutton"),m=h.find(".ui-volumecontrol"),n=m.find(".ui-volumebar"),o=m.find(".ui-guide"),p=m.find(".ui-handle"),q=h.find(".ui-fullscreenbutton"),r=h.find(".ui-seekbar"),s=r.find(".ui-duration"),t=r.find(".ui-currenttime"),u=a(b);d.bind("loadedmetadata.multimediaview",function(a){isNaN(f.duration)||k.find("p").text(c._convertTimeFormat(f.duration)),c._resize()}).bind("timeupdate.multimediaview",function(a){c._updateSeekBar()}).bind("play.multimediaview",function(a){i.removeClass("ui-play-icon").addClass("ui-pause-icon")}).bind("pause.multimediaview",function(a){i.removeClass("ui-pause-icon").addClass("ui-play-icon")}).bind("ended.multimediaview",function(a){(typeof f.loop=="undefined"||f.loop==="")&&c.stop()}).bind("volumechange.multimediaview",function(a){f.muted&&f.volume>.1?(l.removeClass("ui-volume-icon").addClass("ui-mute-icon"),c._reserveVolume=f.volume,f.volume=0):c._reserveVolume!==-1&&!f.muted?(l.removeClass("ui-mute-icon").addClass("ui-volume-icon"),f.volume=c._reserveVolume,c._reserveVolume=-1):f.volume<.1?l.removeClass("ui-volume-icon").addClass("ui-mute-icon"):l.removeClass("ui-mute-icon").addClass("ui-volume-icon"),c.isVolumeHide||c._updateVolumeState()}).bind("durationchange.multimediaview",function(a){isNaN(f.duration)||k.find("p").text(c._convertTimeFormat(f.duration)),c._resize()}).bind("click.multimediaview",function(a){if(!c.options.controls)return;h.fadeToggle("fast"),c._resize()}).bind("multimediaviewinit",function(a){e.controls&&h.show(),c._resize()}),i.bind("click.multimediaview",function(){c._endTimer(),f.paused?f.play():f.pause(),g&&c._startTimer()}),q.bind("click.multimediaview",function(a){a.preventDefault(),c.fullScreen(!c.options.fullScreen),c._resize(),c._endTimer(),a.stopPropagation()}),r.bind("vmousedown.multimediaview",function(a){var b=a.clientX,d=f.duration,e=s.offset(),g=s.width(),h=(b-e.left)/g,i=d*h;if(!f.played.length)return;f.currentTime=i,c._endTimer(),a.preventDefault(),u.bind("vmousemove.multimediaview",function(a){var b=a.clientX,c=(b-e.left)/g;f.currentTime=d*c,a.preventDefault()}).bind("vmouseup.multimediaview",function(){u.unbind("vmousemove.multimediaview vmouseup.multimediaview"),f.paused?f.pause():f.play()})}),l.bind("click.multimediaview",function(){if(c.isVolumeHide){var a=c.element,b=f.volume;c.isVolumeHide=!1,m.fadeIn("fast",function(){c._updateVolumeState(),c._updateSeekBar()}),c._resize()}else c.isVolumeHide=!0,m.fadeOut("fast",function(){c._resize()})}),n.bind("vmousedown.multimediaview",function(a){var b=a.clientX,d=o.offset().left,e=o.width(),f=d+e,g=p.offset(),h=(b-d)/e,i=(b-d)/e;c._endTimer(),c._setVolume(i.toFixed(2)),a.preventDefault(),u.bind("vmousemove.multimediaview",function(a){var b=a.clientX,f=(b-d)/e;c._setVolume(f.toFixed(2)),a.preventDefault()}).bind("vmouseup.multimediaview",function(){u.unbind("vmousemove.multimediaview vmouseup.multimediaview")})})},_removeEvent:function(){var a=this.element,b=a.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),c=b.find(".ui-playpausebutton"),d=b.find(".ui-fullscreenbutton"),e=b.find(".ui-seekbar"),f=b.find(".ui-volumecontrol"),g=f.find(".ui-volumebar"),h=f.find(".ui-handle");a.unbind(".multimediaview"),c.unbind(".multimediaview"),d.unbind(".multimediaview"),e.unbind(".multimediaview"),g.unbind(".multimediaview"),h.unbind(".multimediaview")},_createControl:function(){var b=this.element,c=b[0],d=a("<span></span>").addClass("ui-multimediaview-control"),e=a("<span></span>").addClass("ui-playpausebutton ui-button ui-play-icon"),f=a("<span></span>").addClass("ui-seekbar ui-multimediaview-bar"),g=a("<span><p>00:00:00</p></span>").addClass("ui-timestamplabel"),h=a("<span><p>00:00:00</p></span>").addClass("ui-durationlabel"),i=a("<span></span>").addClass("ui-volumebutton ui-button"),j=a("<span></span>").addClass("ui-volumecontrol"),k=a("<div></div>").addClass("ui-volumebar ui-multimediaview-bar"),l=a("<span></span>").addClass("ui-guide ui-multimediaview-bar-bg"),m=a("<span></span>").addClass("ui-value ui-multimediaview-bar-highlight"),n=a("<span></span>").addClass("ui-handle"),o=a("<span></span>").addClass("ui-fullscreenbutton ui-button"),p=a("<span></span>").addClass("ui-duration ui-multimediaview-bar-bg"),q=a("<span></span>").addClass("ui-currenttime ui-multimediaview-bar-highlight");return f.append(p).append(q).append(h).append(g),i.addClass(c.muted?"ui-mute-icon":"ui-volume-icon"),k.append(l).append(m).append(n),j.append(k),d.append(e).append(f).append(j).append(i),this._isVideo&&(a(o).addClass("ui-fullscreen-on"),d.append(o)),j.hide(),d},_startTimer:function(a){this._endTimer(),a||(a=3e3);var b=this,c=b.element,d=c.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),e=d.find(".ui-volumecontrol");b.controlTimer=setTimeout(function(){b.isVolumeHide=!0,b.controlTimer=null,e.hide(),d.fadeOut("fast")},a)},_endTimer:function(){this.controlTimer&&(clearTimeout(this.controlTimer),this.controlTimer=null)},_convertTimeFormat:function(b){if(!a.isNumeric(b))return"Playback Error";var c=parseInt(b%60,10).toString(),d=parseInt(b/60%60,10).toString(),e=parseInt(b/3600,10).toString(),f=(e.length<2?"0"+e:e)+":"+(d.length<2?"0"+d:d)+":"+(c.length<2?"0"+c:c);return f},
+_updateSeekBar:function(a){var b=this.element,c=b[0],d=c.duration,e=b.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),f=e.find(".ui-seekbar"),g=f.find(".ui-duration"),h=f.find(".ui-currenttime"),i=e.find(".ui-timestamplabel"),j=g.offset(),k=g.width(),l=g.height(),m=0;typeof a=="undefined"&&(a=c.currentTime),m=parseInt(a/d*k,10),g.offset(j),h.offset(j).width(m),i.find("p").text(this._convertTimeFormat(a))},_updateVolumeState:function(){var a=this.element,b=a.parent(".ui-multimediaview-wrap").find(".ui-multimediaview-control"),c=b.find(".ui-volumecontrol"),d=b.find(".ui-volumebutton"),e=c.find(".ui-volumebar"),f=c.find(".ui-guide"),g=c.find(".ui-value"),h=c.find(".ui-handle"),i=h.width(),j=h.height(),k=f.height(),l=f.width(),m=0,n=0,o=0,p=null,q=a[0].volume;m=parseInt(f.offset().top,10),n=parseInt(f.offset().left,10),o=n,p=h.offset(),p.top=m-parseInt((j-k)/2,10),p.left=o+parseInt(l*q,10)-parseInt(i/2,10),h.offset(p),g.offset(f.offset()).width(parseInt(l*q,10))},_setVolume:function(a){var b=this.element[0];if(a<0||a>1)return;b.volume=a},width:function(a){if(this.options.fullScreen)return;var b=this.element,c=b.parent(".ui-multimediaview-wrap");if(arguments.length===0)return b.width();this._isVideo||c.width(a),b.width(a),this._resize()},height:function(a){if(!this._isVideo||this.options.fullScreen)return;var b=this.element;if(arguments.length===0)return b.height();b.height(a),this._resize()},fullScreen:function(a){if(!this._isVideo)return;var b=this.element,c=this.options;if(arguments.length===0)return c.fullScreen;b.parents(".ui-scrollview-clip").scrollview("scrollTo",0,0),this.options.fullScreen=a,this._resize()},refresh:function(){this._resize()}}),a(b).bind("pagecreate create",function(b){a.tizen.multimediaview.prototype.enhanceWithin(b.target)}).bind("pagechange",function(b){a(b.target).find(".ui-multimediaview").each(function(){var b=a(this),c=b[0];c.autoplay&&c.play(),b.multimediaview("refresh")})}).bind("pagebeforechange",function(b){a(b.target).find(".ui-multimediaview").each(function(){var b=a(this),c=b[0],d=b.multimediaview("fullScreen");d&&b.multimediaview("fullScreen",!d),c.played.length!==0&&c.pause()})}),a(c).bind("resize orientationchange",function(b){a(".ui-page-active").find(".ui-multimediaview").multimediaview("refresh")})}(jQuery,document,window),ensureNS("jQuery.mobile.tizen"),function(){jQuery.extend(jQuery.mobile.tizen,{disableSelection:function(a){return this.enableSelection($(a).find("*").not('input, [type="text"], textarea'),"none"),!0},enableSelection:function(a,b){var c;switch(b){case"text":case"auto":case"none":c=b;break;default:c="auto"}return $(a).css({"user-select":c,"-moz-user-select":c,"-webkit-user-select":c,"-o-user-select":c,"-ms-transform":c})},disableContextMenu:function(a){var b=this;$(a).find("*").each(function(){$(this).get(0).tagName!=="INPUT"&&$(this).attr("type")!=="text"&&$(this).get(0).tagName!=="TEXTAREA"&&b._disableContextMenu(this)})},_disableContextMenu:function(a){$(a).each(function(){$(this).bind("contextmenu",function(a){return!1})})},enableContextMenu:function(a){$(a).each(function(){$(this).unbind("contextmenu")})},documentRelativeCoordsFromEvent:function(a){var b=a?a:window.event,c={x:b.clientX,y:b.clientY},d={x:b.pageX,y:b.pageY},e=0,f=0;b.type.match(/^touch/)&&(d={x:b.originalEvent.targetTouches[0].pageX,y:b.originalEvent.targetTouches[0].pageY},c={x:b.originalEvent.targetTouches[0].clientX,y:b.originalEvent.targetTouches[0].clientY});if(d.x||d.y)e=d.x,f=d.y;else if(c.x||c.y)e=c.x+document.body.scrollLeft+document.documentElement.scrollLeft,f=c.y+document.body.scrollTop+document.documentElement.scrollTop;return{x:e,y:f}},targetRelativeCoordsFromEvent:function(a){var b={x:a.offsetX,y:a.offsetY};if(b.x===undefined||isNaN(b.x)||b.y===undefined||isNaN(b.y)){var c=$(a.target).offset();b=$.mobile.tizen.documentRelativeCoordsFromEvent(a),b.x-=c.left,b.y-=c.top}return b}})}(),function(a,b,c,d){function e(a,b){var c=a%b;return c<0&&(c=b+c),c}function f(b){this.options=a.extend({},b),this.easing="easeOutQuad",this.reset()}function l(){return Date.now()}var g={scrolling:0,done:1},h=0,i=1,j=-1,k=/src\s*=\s*[\"\'][\w\/.]+.[A-z]+[\"\']/;a.extend(f.prototype,{start:function(a,b,c){this.state=b!==0?g.scrolling:g.done,this.pos=a,this.speed=b,this.duration=c,this.fromPos=0,this.toPos=0,this.startTime=l()},reset:function(){this.state=g.done,this.pos=0,this.speed=0,this.duration=0},update:function(){var b=this.state,c,d,e,f;return b==g.done?this.pos:(c=this.duration,d=l()-this.startTime,d=d>c?c:d,e=this.speed*(1-a.easing[this.easing](d/c,d,0,1,c)),f=this.pos+e/2,this.pos=f,d>=c&&(this.state=g.done),this.pos)},done:function(){return this.state==g.done},getPosition:function(){return this.pos}}),jQuery.widget("mobile.virtualgrid",jQuery.mobile.widget,{options:{template:"",direction:"y",rotation:!1},create:function(){this._create.apply(this,arguments)},_create:function(b){a.extend(this,{_$view:null,_$clip:null,_$rows:null,_tracker:null,_viewSize:0,_clipSize:0,_cellSize:d,_currentItemCount:0,_itemCount:1,_inheritedSize:null,_timerInterval:0,_timerID:0,_timerCB:null,_lastMove:null,_itemData:function(a){return null},_numItemData:0,_cacheItemData:function(a,b){},_totalRowCnt:0,_templateText:null,_maxViewSize:0,_modifyViewPos:0,_maxSizeExceptClip:0,_maxSize:0,_direction:!1,_didDrag:!0,_reservedPos:0,_scalableSize:0,_eventPos:0,_nextPos:0,_movePos:0,_lastY:0,_speedY:0,_lastX:0,_speedX:0,_rowsPerView:0,_fragment:null,_filterRatio:.9,_overflowStartPos:0,_overflowDir:0,_overflowMaxDragDist:100});var e=this,f=a(e.element),g=e.options,h=null;if(!b)return;if(!e._loadData(b))return;e._fragment=c.createDocumentFragment(),e._inheritedSize=e._getinheritedSize(e.element),e._direction=g.direction==="x"?!0:!1,e._$clip=f.addClass("ui-scrollview-clip").addClass("ui-virtualgrid-view"),h=a(c.createElement("div")).addClass("ui-scrollview-view"),e._clipSize=e._calculateClipSize(),e._$clip.append(h),e._$view=h,e._$clip.css("overflow","hidden"),e._$view.css("overflow","hidden"),e._scrollView=a.tizen.scrollview.prototype,e._initScrollView(),e._createTracker(),e._makePositioned(e._$clip),e._timerInterval=1e3/e.options.fps,e._timerID=0,e._timerCB=function(){e._handleMomentumScroll()},f.closest(".ui-content").addClass("ui-virtualgrid-content").css("overflow","hidden"),e._addBehaviors(),e._currentItemCount=0,e._createOverflowArea(),e._createScrollBar(),e.refresh()},_loadData:function(a){var b=this;if(!a.itemData||typeof a.itemData!="function")return!1;b._itemData=a.itemData;if(!a.numItemData)return!1;if(typeof a.numItemData=="function")b._numItemData=a.numItemData();else{if(typeof a.numItemData!="number")return!1;b._numItemData=a.numItemData}return b._getObjectNames(b._itemData(0)),!0},_initLayout:function(){var a=this,b=a.options,c,d;for(c=-1;c<a._rowsPerView+1;c+=1)d=a._$rows[e(c,a._$rows.length)],a._$view.append(d);a._setElementTransform(-a._cellSize),a._replaceRow(a._$view[0].firstChild,a._totalRowCnt-1),b.rotation&&a._rowsPerView>=a._totalRowCnt&&a._replaceRow(a._$view[0].lastChild,0),a._setViewSize()},_setViewSize:function(){var a=this,b=0,c=0;a._direction?(c=a._cellSize*(a._rowsPerView+2),c=parseInt(c,10)+1,a._$view.width(c),a._viewSize=a._$view.width()):(a._$view.height(a._cellSize*(a._rowsPerView+2)),a._$clip.height(a._clipSize),a._viewSize=a._$view.height())},_getViewWidth:function(){var a=this;return a._maxSize},_getViewHeight:function(){var a=this;return a._maxSize},refresh:function(){var b=this,c=b.options,d=0,e=0,f=null;f=a("#"+c.template);if(!f)return;b._templateText=b._insertAriaAttrToTmpl(f.text()),d=b._calculateClipWidth(),e=b._calculateClipHeight(),b._$view.width(d).height(e),b._$clip.width(d).height(e),b._clipSize=b._calculateClipSize(),b._calculateColumnSize(),b._initPageProperty(),b._setScrollBarSize()},_initPageProperty:function(){var b=this,c=0,d,e=0,f=0,g=b._direction?"width":"height";e=b._calculateColumnCount(),f=parseInt(b._numItemData/e,10),b._totalRowCnt=b._numItemData%e===0?f:f+1,b._itemCount=e;if(b._cellSize<=0)return;c=b._clipSize/b._cellSize,c=Math.ceil(c),b._rowsPerView=parseInt(c,10),d=a(b._makeRows(c+2)),b._$view.append(d.children()),b._$view.children().css(g,b._cellSize+"px"),b._$rows=b._$view.children().detach(),b._reservedPos=-b._cellSize,b._scalableSize=-b._cellSize,b._initLayout(),b._blockScroll=b._rowsPerView>b._totalRowCnt,b._maxSizeExceptClip=(b._totalRowCnt-b._rowsPerView)*b._cellSize,b._maxSize=b._totalRowCnt*b._cellSize,b._maxViewSize=b._rowsPerView*b._cellSize,b._modifyViewPos=-b._cellSize,b._clipSize<b._maxViewSize&&(b._modifyViewPos=-b._cellSize+(b._clipSize-b._maxViewSize))},_getinheritedSize:function(b){var c=a(b),d,e,f={ELEMENT_NODE:1,TEXT_NODE:3},g={isDefinedWidth:!1,isDefinedHeight:!1,width:0,height:0};while(c[0].nodeType===f.ELEMENT_NODE&&(g.isDefinedWidth===!1||g.isHeightDefined===!1)){d=c[0].style.height,e=c[0].style.width,g.isDefinedHeight===!1&&d!==""&&(g.isDefinedHeight=!0,g.height=parseInt(d,10)),g.isDefinedWidth===!1&&e!==""&&(g.isDefinedWidth=!0,g.width=parseInt(e,10)),c=c.parent();if(c.hasClass("ui-content"))break}return g},_resize:function(){var a=this,b=null,c=0,d=0,e=0,f=0,g=0,h=0,i=0,j=0,k=null,l=0;a._direction?(l=a._calculateClipHeight(),a._$view.height(l),a._$clip.height(l)):(l=a._calculateClipWidth(),a._$view.width(l),a._$clip.width(l)),d=a._calculateColumnCount(),d!=a._itemCount&&(e=parseInt(a._numItemData/d,10),a._totalRowCnt=a._numItemData%d===0?e:e+1,h=a._itemCount,a._itemCount=d,i=a._getClipPosition(),a._$view.hide(),f=a._replaceRows(d,h,a._totalRowCnt,i),a._maxSizeExceptClip=(a._totalRowCnt-a._rowsPerView)*a._cellSize,a._maxSize=a._totalRowCnt*a._cellSize,a._scalableSize+=-f*a._cellSize,a._reservedPos+=-f*a._cellSize,a._setScrollBarSize(),a._setScrollBarPosition(f),a._$view.show()),g=a._calculateClipSize(),g!==a._clipSize&&(c=g/a._cellSize,c=parseInt(Math.ceil(c),10),c>a._rowsPerView?a._increaseRow(c-a._rowsPerView):c<a._rowsPerView&&a._decreaseRow(a._rowsPerView-c),a._$rows=a._$view.children(),a._$rows.sort(function(a,b){return a.getAttribute("row-index")-b.getAttribute("row-index")}),a._rowsPerView=c,a._clipSize=g,a._blockScroll=a._rowsPerView>a._totalRowCnt,a._maxSizeExceptClip=(a._totalRowCnt-a._rowsPerView)*a._cellSize,a._maxSize=a._totalRowCnt*a._cellSize,a._maxViewSize=a._rowsPerView*a._cellSize,a._clipSize<a._maxViewSize&&(a._modifyViewPos=-a._cellSize+(a._clipSize-a._maxViewSize)),a._direction?a._$clip.width(a._clipSize):a._$clip.height(a._clipSize),a._setScrollBarSize(),a._setScrollBarPosition(0),a._setViewSize())},resize:function(){var b=this,c=0,d=a(".ui-virtualgrid-view");b._inheritedSize=b._getinheritedSize(b.element),d.length!==0&&b._resize()},_initScrollView:function(){var b=this,c=b.options.direction;a.extend(b.options,b._scrollView.options),b.options.direction=c,b.options.moveThreshold=10,b.options.showScrollBars=!1,b._getScrollHierarchy=b._scrollView._getScrollHierarchy,b._makePositioned=b._scrollView._makePositioned,b._set_scrollbar_size=b._scrollView._set_scrollbar_size,b._setStyleTransform=b._scrollView._setElementTransform,b._hideOverflowIndicator=b._scrollView._hideOverflowIndicator,b._showOverflowIndicator=b._scrollView._showOverflowIndicator,b._setGestureScroll=b._scrollView._setGestureScroll},_createTracker:function(){var a=this;a._tracker=new f(a.options),a._direction?(a._hTracker=a._tracker,a._$clip.width(a._clipSize)):(a._vTracker=a._tracker,a._$clip.height(a._clipSize))},_createOverflowArea:function(){var b=this,c='<div class="ui-virtualgrid-overflow-indicator-',d='-top"></div>',e='-bottom"></div>';if(b.options.rotation)return;b._direction?(b._overflowTop=a(c+"x"+d),b._overflowBottom=a(c+"x"+e)):(b._overflowTop=a(c+"y"+d),b._overflowBottom=a(c+"y"+e)),b._$clip.append(b._overflowTop),b._$clip.append(b._overflowBottom),b._overflowDisplayed=!1},_hideVGOverflowIndicator:function(){if(this._overflowDisplayed===!1)return;this._overflowTop.animate({opacity:0},300),this._overflowBottom.animate({opacity:0},300),this._overflowDisplayed=!1},_createScrollBar:function(){var a=this,b='<div class="ui-scrollbar ui-scrollbar-',c='"><div class="ui-scrollbar-track"><div class="ui-scrollbar-thumb"></div></div></div>';if(a.options.rotation)return;a._direction?(a._$clip.append(b+"x"+c),a._hScrollBar=a._$clip.children(".ui-scrollbar-x"),a._hScrollBar.find(".ui-scrollbar-thumb").addClass("ui-scrollbar-thumb-x")):(a._$clip.append(b+"y"+c),a._vScrollBar=a._$clip.children(".ui-scrollbar-y"),a._vScrollBar.find(".ui-scrollbar-thumb").addClass("ui-scrollbar-thumb-y"))},_setScrollBarSize:function(){var a=this,b=0,c=0,d,e,f;if(a.options.rotation)return;b=parseInt(a._maxViewSize/a._clipSize,10),a._direction?(d=a._hScrollBar.find(".ui-scrollbar-thumb"),e="width",c=d.width(),f="ui-scrollbar-thumb-x",a._hScrollBar.css("width",a._clipSize)):(d=a._vScrollBar.find(".ui-scrollbar-thumb"),e="height",f="ui-scrollbar-thumb-y",c=d.height(),a._vScrollBar.css("height",a._clipSize)),b>c?(d.removeClass(f),d.css(e,b)):b=c,a._itemScrollSize=parseFloat((a._clipSize-b)/(a._totalRowCnt-a._rowsPerView)),a._itemScrollSize=Math.round(a._itemScrollSize*100)/100},_setScrollBarPosition:function(a,b){var c=this,d=null,e="0px",f="0px",g;if(c.options.rotation)return;c._currentItemCount=c._currentItemCount+a,c._vScrollBar?(d=c._vScrollBar.find(".ui-scrollbar-thumb"),f=c._currentItemCount*c._itemScrollSize+"px"):(d=c._hScrollBar.find(".ui-scrollbar-thumb"),e=c._currentItemCount*c._itemScrollSize+"px"),c._setStyleTransform(d,e,f,b)},_hideScrollBars:function(){var a=this,b="ui-scrollbar-visible";if(a.options.rotation)return;a._vScrollBar?a._vScrollBar.removeClass(b):a._hScrollBar.removeClass(b)},_showScrollBars:function(){var a=this,b="ui-scrollbar-visible";if(a.options.rotation)return;a._vScrollBar?a._vScrollBar.addClass(b):a._hScrollBar.addClass(b)},centerTo:function(b){var c=this,d=null,e=null,f=-1,g=c._$rows.length,h,i;if(!c.options.rotation)return;for(i=0;i<g;++i){d=a(c._$rows[i]),e=d.children("."+b);if(e.length){f=parseInt(d.attr("row-index"),10);break}}if(f===-1){f=c._getTargetRowIndex(b);if(f===-1)return}h=-(f*c._cellSize-(c._clipSize-c._cellSize)/2),c._direction?c.scrollTo(h,0):c.scrollTo(0,h)},_getTargetRowIndex:function(a){var b=this,c=b._numItemData,d=b._itemCount,e=b._direction?"top":"left",f="",g=b._totalRowCnt,h;for(h=0;h<c;++h){f=b._makeHtmlData(h,h%d,e);if(b._hasClassItem(f,a)){g=parseInt(h/d,10);break}}return g===b._totalRowCnt?-1:g},_hasClassItem:function(a,b){var c=this,d=c._getItemClass(a);return d.indexOf(b)===-1?!1:d.indexOf("virtualgrid-item")===-1?!1:!0},_getItemClass:function(a){var b=a.indexOf("class"),c=Math.min(a.indexOf('"',b),a.indexOf("'",b)),d=Math.min(a.indexOf('"',c+1),a.indexOf("'",c+1));return a.slice(c+1,d)},scrollTo:function(a,b,c){var d=this;d._direction?(a-=d._cellSize,d._sx=d._reservedPos,d._reservedPos=a):(b-=d._cellSize,d._sy=d._reservedPos,d._reservedPos=b),d._scrollView.scrollTo.apply(this,[a,b,c])},getScrollPosition:function(){return this.direction?{x:-this._ry,y:0}:{x:0,y:-this._ry}},_setScrollPosition:function(a,b){var c=this,d=c._scalableSize,f=c._direction?a:b,g=f-d,k=parseInt(g/c._cellSize,10),l=0,m=0,n=0,o=c._rowsPerView+2,p=c._$view[0];if(c._blockScroll){g>0&&f>=-c._cellSize&&c._scalableSize>=-c._cellSize&&(c._overflowDir=i),g<0&&c._scalableSize<=-(c._maxSizeExceptClip+c._cellSize)&&(c._overflowDir=j);return}if(!c.options.rotation){if(g>0&&f>=-c._cellSize&&c._scalableSize>=-c._cellSize){c._stopMScroll(),c._scalableSize=-c._cellSize,c._setElementTransform(-c._cellSize),c._overflowDir===h&&(c._overflowDir=i);return}if(g<0&&c._scalableSize<=-(c._maxSizeExceptClip+c._cellSize)){c._stopMScroll(),c._scalableSize=-(c._maxSizeExceptClip+c._cellSize),c._setElementTransform(c._modifyViewPos),c._overflowDir===h&&(c._overflowDir=j);return}}n=Math.abs(k)<o?0:k>0?k-o:k+o;if(k>0)for(l=n;l<k;++l)m=-parseInt(d/c._cellSize+l+3,10),c._replaceRow(p.lastChild,e(m,c._totalRowCnt)),p.insertBefore(p.lastChild,p.firstChild);else if(k<0)for(l=n;l>k;--l)m=c._rowsPerView-parseInt(d/c._cellSize+l,10),c._replaceRow(p.firstChild,e(m,c._totalRowCnt)),p.insertBefore(p.firstChild,p.lastChild.nextSibling);c._setScrollBarPosition(-k),c._scalableSize+=k*c._cellSize,c._setElementTransform(f-c._scalableSize-c._cellSize)},_setElementTransform:function(a){var b=this,c=0,d=0;b._direction?c=a+"px":d=a+"px",b._setStyleTransform(b._$view,c,d)},_handleMomentumScroll:function(){var a=this,b=a.options,c=!1,d=this._$view,e=0,f=0,g=a._tracker;g&&(g.update(),a._direction?e=g.getPosition():f=g.getPosition(),c=!g.done()),a._setScrollPosition(e,f),b.rotation?a._reservedPos=a._direction?e:f:(c=!g.done(),a._reservedPos=a._direction?e:f,a._reservedPos=a._reservedPos<=-(a._maxSizeExceptClip-a._modifyViewPos)?-(a._maxSizeExceptClip+a._cellSize):a._reservedPos,a._reservedPos=a._reservedPos>-a._cellSize?-a._cellSize:a._reservedPos),a._$clip.trigger(a.options.updateEventName,[{x:e,y:f}]),c?a._timerID=setTimeout(a._timerCB,a._timerInterval):a._stopMScroll()},_startMScroll:function(a,b){var c=this;c._direction?c._sx=c._reservedPos:c._sy=c._reservedPos,c._scrollView._startMScroll.apply(c,[a,b])},_stopMScroll:function(){this._scrollView._stopMScroll.apply(this)},_enableTracking:function(){var a=this;a._$view.bind(a._dragMoveEvt,a._dragMoveCB),a._$view.bind(a._dragStopEvt,a._dragStopCB),a._scrollView._enableTracking.apply(a)},_disableTracking:function(){var a=this;a._$view.unbind(a._dragMoveEvt,a._dragMoveCB),a._$view.unbind(a._dragStopEvt,a._dragStopCB),a._scrollView._disableTracking.apply(a)},_handleDragStart:function(a,b,c){var d=this;d._scrollView._handleDragStart.apply(this,[a,b,c]),d._eventPos=d._direction?b:c,d._nextPos=d._reservedPos},_handleDragMove:function(a,b,c){var d=this,e=b-d._lastX,f=c-d._lastY,g=0,j=0,k=0,m=0,n=0,o=0,p=null;return d._lastMove=l(),d._speedX=e,d._speedY=f,d._didDrag=!0,d._lastX=b,d._lastY=c,d._direction?(d._movePos=b-d._eventPos,g=d._nextPos+d._movePos,o=b):(d._movePos=c-d._eventPos,j=d._nextPos+d._movePos,o=c),d._showScrollBars(),d._setScrollPosition(g,j),d._overflowDir!==h&&(p=d._overflowDir===i?d._overflowTop:d._overflowBottom,d._overflowDisplayed||(d._overflowDisplayed=!0,d._overflowStartPos=o),k=(o-d._overflowStartPos)*d._overflowDir,n=k<0?0:k>d._overflowMaxDragDist?1:k/d._overflowMaxDragDist,p.css("opacity",n)),!1},_handleDragStop:function(a){var b=this;return b._reservedPos=b._movePos?b._nextPos+b._movePos:b._reservedPos,b._scrollView._handleDragStop.apply(this,[a]),b._overflowDir!==h&&(b._overflowDir=h,b._hideVGOverflowIndicator()),b._didDrag?!1:d},_addBehaviors:function(){var d=this;d.options.eventType==="mouse"?(d._dragStartEvt="mousedown",d._dragStartCB=function(a){return d._handleDragStart(a,a.clientX,a.clientY)},d._dragMoveEvt="mousemove",d._dragMoveCB=function(a){return d._handleDragMove(a,a.clientX,a.clientY)},d._dragStopEvt="mouseup",d._dragStopCB=function(a){return d._handleDragStop(a,a.clientX,a.clientY)},d._$view.bind("vclick",function(a){return!d._didDrag})):(d._dragStartEvt="touchstart",d._dragStartCB=function(a){var b=a.originalEvent.targetTouches[0];return d._handleDragStart(a,b.pageX,b.pageY)},d._dragMoveEvt="touchmove",d._dragMoveCB=function(a){var b=a.originalEvent.targetTouches[0];return d._handleDragMove(a,b.pageX,b.pageY)},d._dragStopEvt="touchend",d._dragStopCB=function(a){return d._handleDragStop(a)}),d._$view.bind(d._dragStartEvt,d._dragStartCB),d._$view.delegate(".virtualgrid-item","click",function(b){var c=a(this);c.trigger("select",this)}),a(b).bind("resize",function(b){var c=0,e=a(".ui-virtualgrid-view");e.length!==0&&d._resize()}),a(c).one("pageshow",function(c){var e=a(d.element).parents(".ui-page"),f=e.find(":jqmData(role='header')"),g=e.find(":jqmData(role='footer')"),h=e.find(":jqmData(role='content')"),i=g?g.height():0,j=f?f.height():0;e&&h&&(h.height(b.innerHeight-j-i).css("overflow","hidden"),h.addClass("ui-virtualgrid-content"))})},_calculateClipSize:function(){var a=this,b=0;return a._direction?b=a._calculateClipWidth():b=a._calculateClipHeight(),b},_calculateClipWidth:function(){var c=this,d=c._$clip.parent(),e=0,f=a(b).width();return c._inheritedSize.isDefinedWidth?c._inheritedSize.width:(d.hasClass("ui-content")?(e=parseInt(d.css("padding-left"),10),f-=e||0,e=parseInt(d.css("padding-right"),10),f-=e||0):f=c._$clip.width(),f)},_calculateClipHeight:function(){var c=this,d=c._$clip.parent(),e=null,f=null,g=0,h=a(b).height();return c._inheritedSize.isDefinedHeight?c._inheritedSize.height:(d.hasClass("ui-content")?(g=parseInt(d.css("padding-top"),10),h-=g||0,g=parseInt(d.css("padding-bottom"),10),h-=g||0,e=d.siblings(".ui-header"),f=d.siblings(".ui-footer"),e&&(e.outerHeight(!0)===null?h-=a(".ui-header").outerHeight()||0:h-=e.outerHeight(!0)),f&&(h-=f.outerHeight(!0))):h=c._$clip.height(),h)},_calculateColumnSize:function(){var b=this,c,d;c=a(b._makeRows(1)),b._$view.append(c.children().first()),b._direction?(b._viewSize=b._$view.width(),d=b._$view.children().first().children().first(),b._cellSize=d.outerWidth(!0),b._cellOtherSize=d.outerHeight(!0)):(b._viewSize=b._$view.height(),d=b._$view.children().first().children().first(),b._cellSize=d.outerHeight(!0),b._cellOtherSize=d.outerWidth(!0)),c.remove(),b._$view.children().remove()},_calculateColumnCount:function(){var a=this,b=a._$clip,c=a._direction?b.innerHeight():b.innerWidth(),d=0;return a._direction?c-=parseInt(b.css("padding-top"),10)+parseInt(b.css("padding-bottom"),10):c-=parseInt(b.css("padding-left"),10)+parseInt(b.css("padding-right"),10),d=parseInt(c/a._cellOtherSize,10),d>0?d:1},_getClipPosition:function(){var a=this,b=null,c=null,d=-a._cellSize,e=a._$view.closest(".ui-scrollview-view");return e&&(b=e.css("-webkit-transform"),c=b.substr(7),c=c.substr(0,c.length-1),c=c.split(", "),d=Math.abs(c[5])),d},_makeRows:function(a){var b=this,c=0,d=null,e=null;e=b._createElement("div"),e.setAttribute("class","ui-scrollview-view");for(c=0;c<a;c+=1)d=b._makeRow(c),b._direction&&(d.style.top=0,d.style.left=c*b._cellSize),e.appendChild(d);return e},_makeRow:function(a){var b=this,c=a*b._itemCount,d=0,e=b._direction?"ui-virtualgrid-wrapblock-x":"ui-virtualgrid-wrapblock-y",f=b._createElement("div"),g="",h=b._direction?"top":"left";for(d=0;d<b._itemCount;d++)g+=b._makeHtmlData(c,d,h),c+=1;return f.innerHTML=g,f.setAttribute("class",e),f.setAttribute("row-index",String(a)),b._fragment.appendChild(f),f},_makeHtmlData:function(a,b,c){var d=this,e="",f=null;return f=d._itemData(a),f&&(e=d._getConvertedTmplStr(f),e=d._insertPosToTmplStr(e,c,b*d._cellOtherSize)),e},_insertPosToTmplStr:function(a,b,c){var d=a.indexOf(">"),e=-1,f,g,h,i=!1,j=0,k,l=0;if(d===-1)return;f=a.slice(0,d),g=a.slice(d,a.length),e=f.indexOf("class");if(e!==-1){k=f.length;for(l=e+6;l<k;l++)if(f.charAt(l)==='"'||f.charAt(l)==="'"){if(i!==!1){j=l;break}i=!0}h=f.slice(0,j)+" virtualgrid-item"+f.slice(j,k)+g}else h=f+' class="virtualgrid-item"'+g;return isNaN(c)||(h=h.replace(">",' style="'+b+": "+String(c)+'px">')),h},_increaseRow:function(b){var c=this,d=c.options.rotation,f=c._totalRowCnt,g=c._$view[0],h=null,i=g.lastChild,j=null,k=0,l=0,m;if(!i)return;l=parseInt(i.getAttribute("row-index"),10),d||(h=g.firstChild,k=parseInt(h.getAttribute("row-index"),10));for(m=0;m<b;++m){if(l>=f-1&&!d){if(k==0)break;j=c._makeRow(--k),g.insertBefore(j,h),h=j}else j=c._makeRow(e(++l,f)),g.appendChild(j);c._direction?a(j).width(c._cellSize):a(j).height(c._cellSize)}},_decreaseRow:function(a){var b=this,c=b._$view[0],d;for(d=0;d<a;++d)c.removeChild(c.lastChild)},_replaceRows:function(b,c,d,f){var g=this,h=g._$view.children(),i=0,j=0,k=0,l=1,m=g._filterRatio*g._cellSize+g._cellSize,n=0;m<f&&(l+=1),i=parseInt(a(h[l]).attr("row-index"),10),i===0?j=d-l:(j=Math.round(i*c/b),j+g._rowsPerView>=d&&(j=d-g._rowsPerView),k=i-j,j-=l);for(n=0;n<h.length;n+=1)g._replaceRow(h[n],e(j,g._totalRowCnt)),j++;return-k},_replaceRow:function(a,b){var c=this,d=null;while(a.hasChildNodes())a.removeChild(a.lastChild);d=c._makeRow(b);while(d.children.length)a.appendChild(d.children[0]);a.setAttribute("row-index",d.getAttribute("row-index")),d.parentNode.removeChild(d)},_createElement:function(a){var b=c.createElement(a);return this._fragment.appendChild(b),b},_getObjectNames:function(a){var b=[],c="";for(c in a)b.push(c);this._properties=b},_getConvertedTmplStr:function(a){var b=this,c=b._properties,d=0,e,f="";if(!a)return;e=b._templateText;for(d=0;d<c.length;d++)e=b._strReplace(e,"${"+c[d]+"}",a[c[d]]);return e=b._changeImgSrcAriaAttrFromTmpl(e),e},_changeImgSrcAriaAttrFromTmpl:function(a){var b=this,c="",d,e="",f="",g,h,i,j;i=a,d=i.indexOf("$ARIA-IMG-SRC-ALT$");while(d!==-1)g="",e+=i.slice(0,d+19),f=i.slice(d+19,i.length),j=f.match(k),j&&(h=j[0].lastIndexOf("/"),h!==-1&&(g=j[0].slice(h+1,-1))),e=e.replace("$ARIA-IMG-SRC-ALT$",g),i=f,d=i.indexOf("$ARIA-IMG-SRC-ALT$"),c=e+f;return c===""&&(c=a),c},_insertAriaAttrToTmpl:function(a){var b="",c,d="",e="",f;f=a.replace("<div",'<div tabindex="0" aria-selected="true"'),c=f.indexOf("<img");if(c!==-1){while(c!==-1)d+=f.slice(0,c+4),e=f.slice(c+4,f.length),d+=' role="img" alt="$ARIA-IMG-SRC-ALT$"',f=e,c=f.indexOf("<img"),b=d+e;f=b,c=f.indexOf("<span"),d="";while(c!==-1)d+=f.slice(0,c+5),e=f.slice(c+5,f.length),d+=' aria-hidden="true" tabindex="-1"',f=e,c=f.indexOf("<span"),b=d+e}return b===""&&(b=a),b},_strReplace:function(a,b,c){var d=a,e=a.indexOf(b);while(e!==-1)d=d.replace(b,c),e=d.indexOf(b);return d}}),a(c).bind("pagecreate create",function(b){a(":jqmData(role='virtualgrid')").virtualgrid()})}(jQuery,window,document),function(a,b){function c(){var b=a("script[data-framework-version][data-framework-root][data-framework-theme]");return b.attr("data-framework-root")+"/"+b.attr("data-framework-version")+"/themes/"+b.attr("data-framework-theme")+"/proto-html"}a.widget("tizen.widgetex",a.mobile.widget,{_createWidget:function(){a.tizen.widgetex.loadPrototype.call(this,this.namespace+"."+this.widgetName),a.mobile.widget.prototype._createWidget.apply(this,arguments)},_init:function(){if(this.element===b)return;var c=this.element.closest(".ui-page"),d=this,e={};c.is(":visible")?this._realize():c.bind("pageshow",function(){d._realize()}),a.extend(e,this.options),this.options={},this._setOptions(e)},_getCreateOptions:function(){if(this.element.is("input")&&this._value!==b){var c=this.element.attr("type")==="checkbox"||this.element.attr("type")==="radio"?this.element.is(":checked"):this.element.is("[value]")?this.element.attr("value"):b;c!=b&&this.element.attr(this._value.attr,c)}return a.mobile.widget.prototype._getCreateOptions.apply(this,arguments)},_setOption:function(c,d){var e="_set"+c.replace(/^[a-z]/,function(a){return a.toUpperCase()});this[e]!==b?this[e](d):a.mobile.widget.prototype._setOption.apply(this,arguments)},_setDisabled:function(b){a.Widget.prototype._setOption.call(this,"disabled",b),this.element.is("input")&&this.element.attr("disabled",b)},_setValue:function(b){a.tizen.widgetex.setValue(this,b)},_realize:function(){}}),a.tizen.widgetex.setValue=function(a,c){if(a._value!==b){var d=a._value.makeString?a._value.makeString(c):c,e;a.element.attr(a._value.attr,d),a._value.signal!==b&&a.element.triggerHandler(a._value.signal,c),a.element.is("input")&&(e=a.element.attr("type"),e==="checkbox"||e==="radio"?c?a.element.attr("checked",!0):a.element.removeAttr("checked"):a.element.attr("value",d),a.element.trigger("change"))}},a.tizen.widgetex.assignElements=function(b,c){var d={},e;for(e in c)typeof c[e]=="string"?(d[e]=b.find(c[e]),c[e].match(/^#/)&&d[e].removeAttr("id")):typeof c[e]=="object"&&(d[e]=a.tizen.widgetex.assignElements(b,c[e]));return d},a.tizen.widgetex.loadPrototype=function(d,e){var f=d.split("."),g,h,i,j=!1,k,l;f.length==2&&(g=f[0],h=f[1],a[g][h].prototype._htmlProto!==b&&(i=a[g][h].prototype._htmlProto.source,i===b&&(i=h,j=!0),typeof i=="string"?j?(d=i,l=c(),a.ajax({url:l+"/"+d+".prototype.html",async:!1,dataType:"html"}).success(function(b,c,d){i=a("<div></div>").html(b).jqmData("tizen.widgetex.ajax.fail",!1)}),i=a("<div></div>").text("Failed to load proto for widget "+g+"."+h+"!").css({background:"red",color:"blue",border:"1px solid black"}).jqmData("tizen.widgetex.ajax.fail",!0)):i=a(i).jqmData("tizen.widgetex.ajax.fail",!1):i.jqmData("tizen.widgetex.ajax.fail",!1),k=i,a[g][h].prototype._htmlProto.source=i,a[g][h].prototype._htmlProto.ui!==b&&a.extend(this,{_ui:a.tizen.widgetex.assignElements(k.clone(),a[g][h].prototype._htmlProto.ui)})))}}(jQuery),function(a,b){var c={},d=0,e=1,f=-1;a.widget("tizen.virtuallistview",a.mobile.widget,{options:{theme:"s",countTheme:"s",headerTheme:"s",dividerTheme:"s",splitIcon:"arrow-r",splitTheme:"s",inset:!1,id:"",childSelector:" li",dbtable:"",template:"",dbkey:!1,scrollview:!1,row:100,page_buf:30,initSelector:":jqmData(role='virtuallistview')"},_stylerMouseUp:function(){a(this).addClass("ui-btn-up-s"),a(this).removeClass("ui-btn-down-s")},_stylerMouseDown:function(){a(this).addClass("ui-btn-down-s"),a(this).removeClass("ui-btn-up-s")},_stylerMouseOver:function(){a(this).toggleClass("ui-btn-hover-s")},_stylerMouseOut:function(){a(this).toggleClass("ui-btn-hover-s"),a(this).addClass("ui-btn-up-s"),a(this).removeClass("ui-btn-down-s")},_pushData:function(b){var c=this.options,d,e=a("#"+b),f=c.row>this._numItemData?this._numItemData:c.row,g;for(d=0;d<f;d++)g=e.tmpl(this._itemData(d)),a(c.id).append(a(g).attr("id",c.itemIDPrefix+d));a(c.id).trigger("create")},_reposition:function(b){var c,d=this,e,f;b.data?c=b.data:c=b,a(c.id+c.childSelector).size()>0&&(d._title_h=a(c.id+c.childSelector+":first").position().top,d._line_h=a(c.id+c.childSelector+":first").outerHeight(),d._container_w=a(c.id).innerWidth(),e=parseInt(a(c.id+c.childSelector).css("padding-left"),10)+parseInt(a(c.id+c.childSelector).css("padding-right"),10),a(c.id+">"+c.childSelector).addClass("position_absolute").addClass("ui-btn-up-s").bind("mouseup",d._stylerMouseUp).bind("mousedown",d._stylerMouseDown).bind("mouseover",d._stylerMouseOver).bind("mouseout",d._stylerMouseOut)),a(c.id+">"+c.childSelector).each(function(b){f=parseInt(a(this).css("margin-left"),10)+parseInt(a(this).css("margin-right"),10),a(this).css("top",d._title_h+d._line_h*b+"px").css("width",d._container_w-e-f)}),a(c.id).height(d._numItemData*d._line_h)},_resize:function(b){var c,d=this,e,f,g;b.data?c=b.data:c=b,e=a(c).children(c.childSelector),d._container_w=a(c).width(),f=parseInt(e.css("padding-left"),10)+parseInt(e.css("padding-right"),10),e.each(function(b,c){g=parseInt(a(this).css("margin-left"),10)+parseInt(a(this).css("margin-right"),10),a(this).css("width",d._container_w-f-g)})},_scrollmove:function(b){function j(){return d.scrollview?h.viewTop():i.viewTop()}function k(a){var b=!1;b&&console.log(">>virtualllist: "+a)}function l(b,c){function t(b,c,d){var e={ELEMENT_NODE:1,TEXT_NODE:3},f,g,h,i,j;a(c).find(".ui-li-text-main",".ui-li-text-sub",".ui-li-text-sub2","ui-btn-text").each(function(b){f=a(this),h=a(d).find(".ui-li-text-main",".ui-li-text-sub","ui-btn-text").eq(b).text(),a(f).contents().filter(function(){return this.nodeType==e.TEXT_NODE}).get(0).data=h}),a(c).find("img").each(function(b){var c=a(this);i=a(d).find("img").eq(b).attr("src"),a(c).attr("src",i)}),a(c).removeData()}function u(b,c,d){var e,f,g,h;return k(">> move item: "+c+" --> "+d),f=a("#"+b.options.itemIDPrefix+c),!f||!f.length?!1:(h=a("#"+b.options.template),h&&(g=h.tmpl(b._itemData(d)),t(b,f,g),g.remove()),f.css("top",d*b._line_h).attr("id",b.options.itemIDPrefix+d),!0)}var d,e,g,h=b._first_index,i=b._last_index,m,n,o,p,q=b.options.row,r,s;d=j(),r=Math.ceil(q/3),e=Math.floor(d/b._line_h)-r,g=e+q-1,e<0?(g+=-e,e=0):g>b._numItemData-1&&(e-=g-(b._numItemData-1),g=b._numItemData-1),m=e-h,k("cy="+d+", oti="+h+", obi="+i+", cti="+e+", cbi="+g+", dti="+m);if(0==m){b.timerStillCount+=1;if(b.timerStillCount<12){k("dti=0 "+b.timerStillCount+" times"),b.timerMoveID=setTimeout(l,f,b);return}k("dti=0 "+b.timerStillCount+" times. End timer."),b.timerStillCount=0,b.timerMoveID&&(clearTimeout(b.timerMoveID),b.timerMoveID=null)}else{b.timerStillCount=0,Math.abs(m)>=q?(n=h,o=i,p=m,k(">>> WHOLE CHANGE! delta="+p)):(m>0?(n=h,o=h+m-1,p=q):(n=i+m+1,o=i,p=-q),k(">>> partial change. delta="+p));for(s=n;s<=o;s++)u(b,s,s+p);b._first_index=e,b._last_index=g,b.timerMoveID=setTimeout(l,f,b)}return}var c=b.data,d=c.options,e=c._num_top_items,f=100,g,h,i;h={viewTop:function(){var b=a(d.id).parentsUntil(".ui-page").find(".ui-scrollview-view"),c=b.css("-webkit-transform"),e="0,0,0,0,0,0";return c&&(e=c.replace(/matrix\s*\((.*)\)/,"$1")),-parseInt(e.split(",")[5],10)}},i={viewTop:function(){return a(window).scrollTop()}},c.timerStillCount=0,c.timerMoveID&&(clearTimeout(c.timerMoveID),c.timerMoveID=null),l(c)},_recreate:function(b){var c=this,e=this.options;a(e.id).empty(),c._numItemData=b.length,c._direction=d,c._first_index=0,c._last_index=e.row-1,c._pushData(e.template)
+,e.childSelector==" ul"&&a(e.id+" ul").swipelist(),a(e.id).virtuallistview(),c.refresh(!0),c._reposition(e)},_initList:function(){var b=this,c=this.options;b._pushData(c.template),a(c.id).parentsUntil(".ui-page").parent().one("pageshow",function(){setTimeout(function(){b._reposition(c)},0)}),a(document).bind("scrollstart.virtuallist scrollstop.vrituallist",b,b._scrollmove),a(window).on("throttledresize",a(c.id),b._resize),c.childSelector==" ul"&&a(c.id+" ul").swipelist(),b.refresh(!0)},create:function(){var a=this.options;this._create.apply(this,arguments),this._reposition(a)},_create:function(b){a.extend(this,{_itemData:function(a){return null},_numItemData:0,_cacheItemData:function(a,b){},_title_h:0,_container_w:0,_minimum_row:100,_direction:d,_first_index:0,_last_index:0,_num_top_items:0});var c=this,e=this.options,f=this.element,g=a('<div class="ui-virtuallist"/>'),h=a("<ul></ul>"),i=f.find(':jqmData(role="virtuallistview" )'),j=null,k=this,l,m;f.addClass(function(a,b){return b+" ui-listview ui-virtual-list-container"+(c.options.inset?" ui-listview-inset ui-corner-all ui-shadow ":"")}),e.itemIDPrefix=f.attr("id")+"_",e.id="#"+f.attr("id"),a(e.id).bind("pagehide",function(b){a(e.id).empty()}),a(".ui-scrollview-clip").size()>0?e.scrollview=!0:e.scrollview=!1,f.data("row")&&(e.row=f.data("row"),e.row<c._minimum_row&&(e.row=c._minimum_row),e.page_buf=parseInt(e.row/2,10));if(b){if(!b.itemData||typeof b.itemData!="function")return;c._itemData=b.itemData;if(!b.numItemData)return;if(typeof b.numItemData=="function")c._numItemData=b.numItemData();else{if(typeof b.numItemData!="number")return;c._numItemData=b.numItemData}}else{console.warn("WARNING: The data interface of virtuallist is changed. \nOld data interface(data-dbtable) is still supported, but will be removed in next version. \nPlease fix your code soon!");if(!a(e.id).hasClass("vlLoadSuccess"))return;l=f.jqmData("dbtable"),m=window[l],a(e.id).empty(),m||(m={}),c._itemData=function(a){return m[a]},c._numItemData=m.length}f.data("template")&&(e.template=f.data("template"),f.data("swipelist")==1?e.childSelector=" ul":e.childSelector=" li"),f.data("dbkey")&&(e.dbkey=f.data("dbkey")),c._first_index=0,c._last_index=e.row-1,c._initList()},destroy:function(){var b=this.options;a(document).unbind("scrollstop"),a(window).off("throttledresize",this._resize),a(b.id).empty(),this.timerMoveID&&(clearTimeout(this.timerMoveID),this.timerMoveID=null)},_itemApply:function(b,c){var d=c.find(".ui-li-count");d.length&&c.addClass("ui-li-has-count"),d.addClass("ui-btn-up-"+(b.jqmData("counttheme")||this.options.countTheme)+" ui-btn-corner-all"),c.find("h1, h2, h3, h4, h5, h6").addClass("ui-li-heading").end().find("p, dl").addClass("ui-li-desc").end().find(">img:eq(0), .ui-link-inherit>img:eq(0)").addClass("ui-li-thumb").each(function(){c.addClass(a(this).is(".ui-li-icon")?"ui-li-has-icon":"ui-li-has-thumb")}).end().find(".ui-li-aside").each(function(){var b=a(this);b.prependTo(b.parent())})},_removeCorners:function(a,b){var c="ui-corner-top ui-corner-tr ui-corner-tl",d="ui-corner-bottom ui-corner-br ui-corner-bl";a=a.add(a.find(".ui-btn-inner, .ui-li-link-alt, .ui-li-thumb")),b==="top"?a.removeClass(c):b==="bottom"?a.removeClass(d):a.removeClass(c+" "+d)},_refreshCorners:function(a){var b,c,d,e;this.options.inset&&(b=this.element.children("li"),c=a?b.not(".ui-screen-hidden"):b.filter(":visible"),this._removeCorners(b),d=c.first().addClass("ui-corner-top"),d.add(d.find(".ui-btn-inner")).find(".ui-li-link-alt").addClass("ui-corner-tr").end().find(".ui-li-thumb").not(".ui-li-icon").addClass("ui-corner-tl"),e=c.last().addClass("ui-corner-bottom"),e.add(e.find(".ui-btn-inner")).find(".ui-li-link-alt").addClass("ui-corner-br").end().find(".ui-li-thumb").not(".ui-li-icon").addClass("ui-corner-bl"))},refresh:function(b){this.parentPage=this.element.closest(".ui-page"),this._createSubPages();var c=this.options,d=this.element,e=this,f=d.jqmData("dividertheme")||c.dividerTheme,g=d.jqmData("splittheme"),h=d.jqmData("spliticon"),i=d.children("li"),j=a.support.cssPseudoElement||!a.nodeName(d[0],"ol")?0:1,k,l,m,n,o,p,q,r,s,t,u;j&&d.find(".ui-li-dec").remove();for(s=0,t=i.length;s<t;s++){k=i.eq(s),l="ui-li";if(b||!k.hasClass("ui-li"))u=k.jqmData("theme")||c.theme,n=k.children("a"),n.length?(r=k.jqmData("icon"),k.buttonMarkup({wrapperEls:"div",shadow:!1,corners:!1,iconpos:"right",icon:!1,theme:u}),r!=0&&n.length==1&&k.addClass("ui-li-has-arrow"),n.first().addClass("ui-link-inherit"),n.length>1&&(l+=" ui-li-has-alt",o=n.last(),p=g||o.jqmData("theme")||c.splitTheme,o.appendTo(k).attr("title",o.getEncodedText()).addClass("ui-li-link-alt").empty().buttonMarkup({shadow:!1,corners:!1,theme:u,icon:!1,iconpos:!1}).find(".ui-btn-inner").append(a("<span />").buttonMarkup({shadow:!0,corners:!0,theme:p,iconpos:"notext",icon:h||o.jqmData("icon")||c.splitIcon})))):k.jqmData("role")==="list-divider"?(l+=" ui-li-divider ui-btn ui-bar-"+f,k.attr("role","heading"),j&&(j=1)):l+=" ui-li-static ui-body-"+u;j&&l.indexOf("ui-li-divider")<0&&(q=k.is(".ui-li-static:first")?k:k.find(".ui-link-inherit"),q.addClass("ui-li-jsnumbering").prepend("<span class='ui-li-dec'>"+j++ +". </span>")),k.add(k.children(".ui-btn-inner")).addClass(l),e._itemApply(d,k)}this._refreshCorners(b)},_idStringEscape:function(a){return a.replace(/\W/g,"-")},_createSubPages:function(){var b=this.element,d=b.closest(".ui-page"),e=d.jqmData("url"),f=e||d[0][a.expando],g=b.attr("id"),h=this.options,i="data-"+a.mobile.ns,j=this,k=d.find(":jqmData(role='footer')").jqmData("id"),l,m;typeof c[f]=="undefined"&&(c[f]=-1),g=g||++c[f],a(b.find("li>ul, li>ol").toArray().reverse()).each(function(c){var d=this,f=a(this),j=f.attr("id")||g+"-"+c,m=f.parent(),n,p=n.first().getEncodedText(),q=(e||"")+"&"+a.mobile.subPageUrlKey+"="+j,r=f.jqmData("theme")||h.theme,s=f.jqmData("counttheme")||b.jqmData("counttheme")||h.countTheme,t,u;n=a(f.prevAll().toArray().reverse()),n=n.length?n:a("<span>"+a.trim(m.contents()[0].nodeValue)+"</span>"),l=!0,t=f.detach().wrap("<div "+i+"role='page' "+i+"url='"+q+"' "+i+"theme='"+r+"' "+i+"count-theme='"+s+"'><div "+i+"role='content'></div></div>").parent().before("<div "+i+"role='header' "+i+"theme='"+h.headerTheme+"'><div class='ui-title'>"+p+"</div></div>").after(k?a("<div "+i+"role='footer' "+i+"id='"+k+"'>"):"").parent().appendTo(a.mobile.pageContainer),t.page(),u=m.find("a:first"),u.length||(u=a("<a/>").html(n||p).prependTo(m.empty())),u.attr("href","#"+q)}).virtuallistview(),l&&d.is(":jqmData(external-page='true')")&&d.data("page").options.domCache===!1&&(m=function(b,c){var f=c.nextPage,g;c.nextPage&&(g=f.jqmData("url"),g.indexOf(e+"&"+a.mobile.subPageUrlKey)!==0&&(j.childPages().remove(),d.remove()))},d.unbind("pagehide.remove").bind("pagehide.remove",m))},childPages:function(){var b=this.parentPage.jqmData("url");return a(":jqmData(url^='"+b+"&"+a.mobile.subPageUrlKey+"')")}}),a(document).bind("pagecreate create",function(b){a(a.tizen.virtuallistview.prototype.options.initSelector,b.target).virtuallistview()})}(jQuery),function(a,b,c,d){a.widget("tizen.tokentextarea",a.mobile.widget,{_focusStatus:null,_items:null,_viewWidth:0,_reservedWidth:0,_currentWidth:0,_fontSize:0,_anchorWidth:0,_labelWidth:0,_marginWidth:0,options:{label:"To : ",link:null,description:"+ {0}"},_create:function(){var b=this,d=this.element,e=d.jqmData("role"),f=this.options,g="ui-tokentextarea-link",h=a(c.createElement("input")),i=a(c.createElement("span")),j=a(c.createElement("a"));d.hide().empty().addClass("ui-"+e),a(i).text(f.label).addClass("ui-tokentextarea-label").attr("tabindex",0),d.append(i),a(h).addClass("ui-tokentextarea-input ui-tokentextarea-input-visible ui-input-text ui-body-s").attr("role","textbox"),d.append(h);if(f.link===null||a.trim(f.link).length<1||a(f.link).length===0)g+="-dim";a(j).attr("data-role","button").buttonMarkup({inline:!0,icon:"plus",style:"circle"}).attr({href:a.trim(f.link),tabindex:0}).addClass("ui-tokentextarea-link-base").addClass(g).find("span.ui-btn-text").text("Add recipient"),d.append(j),this._bindEvents(),b._focusStatus="init",d.show(),b._viewWidth=d.innerWidth(),b._reservedWidth+=b._calcBlockWidth(j),b._reservedWidth+=b._calcBlockWidth(i),b._fontSize=parseInt(a(j).css("font-size"),10),b._currentWidth=b._reservedWidth,b._modifyInputBoxWidth()},_bindEvents:function(){var b=this,d=b.element,e=b.options,f=d.find(".ui-tokentextarea-input"),g=d.find(".ui-tokentextarea-link-base");d.delegate("div","click",function(c){a(this).hasClass("ui-tokentextarea-sblock")&&b._removeTextBlock();var e=d.find("div.ui-tokentextarea-sblock");typeof e!="undefined"&&e.removeClass("ui-tokentextarea-sblock").addClass("ui-tokentextarea-block"),a(this).removeClass("ui-tokentextarea-block").addClass("ui-tokentextarea-sblock"),d.trigger("select")}),f.bind("keyup",function(c){var d=c.keyCode,e=a(f).val(),g=[],h,i=!1;if(d===8)e.length===0&&b._validateTargetBlock();else if(d===13||d===186||d===188){if(e.length!==0){g=e.split(/[,;]/);for(h=0;h<g.length;h++)g[h].length!==0&&g[h].replace(/\s/g,"").length!==0&&b._addTextBlock(g[h])}f.val(""),i=!0}else b._unlockTextBlock();return!i}),g.click(function(){if(a(g).hasClass("ui-tokentextarea-link-dim"))return;a(f).removeClass("ui-tokentextarea-input-visible").addClass("ui-tokentextarea-input-invisible"),a.mobile.changePage(e.link,{transition:"slide",reverse:!1,changeHash:!1})}),a(c).bind("pagechange.mbe",function(c){if(d.innerWidth()===0)return;b.refresh(),a(f).removeClass("ui-tokentextarea-input-invisible").addClass("ui-tokentextarea-input-visible")}),d.bind("click",function(a){b._focusStatus==="focusOut"&&b.focusIn()})},_addTextBlock:function(b,d){if(arguments.length===0)return;if(!b)return;var e=this,f=e.element,g=b,h=d,i=null,j=null;e._viewWidth===0&&(e._viewWidth=f.innerWidth()),j=a(c.createElement("div")),j.text(g).addClass("ui-tokentextarea-block").attr({"aria-label":"double tap to edit",tabindex:0}),j.css({visibility:"hidden"}),i=f.find("div"),h!==null&&h<=i.length?a(i[h]).before(j):f.find(".ui-tokentextarea-input").before(j),j=e._ellipsisTextBlock(j),j.css({visibility:"visible"}),e._modifyInputBoxWidth(),j.hide(),j.fadeIn("fast",function(){e._currentWidth+=e._calcBlockWidth(j),f.trigger("add")})},_removeTextBlock:function(){var a=this,b=this.element,c=b.find("div.ui-tokentextarea-sblock"),d=null,e=function(){};c!==null&&c.length>0?(a._currentWidth-=a._calcBlockWidth(c),c.fadeOut("fast",function(){c.remove(),a._modifyInputBoxWidth()}),this._eventRemoveCall=!0,b[0].remove&&(d=b[0].remove,b[0].remove=e),b.triggerHandler("remove"),d&&(b[0].remove=d),this._eventRemoveCall=!1):b.find("div:last").removeClass("ui-tokentextarea-block").addClass("ui-tokentextarea-sblock")},_calcBlockWidth:function(b){return a(b).outerWidth(!0)},_unlockTextBlock:function(){var a=this.element,b=a.find("div.ui-tokentextarea-sblock");b&&b.removeClass("ui-tokentextarea-sblock").addClass("ui-tokentextarea-block")},_validateTargetBlock:function(){var a=this,b=a.element,c=b.find("div:last"),d=null;c.hasClass("ui-tokentextarea-sblock")?a._removeTextBlock():(d=b.find("div.ui-tokentextarea-sblock"),d.removeClass("ui-tokentextarea-sblock").addClass("ui-tokentextarea-block"),c.removeClass("ui-tokentextarea-block").addClass("ui-tokentextarea-sblock"))},_ellipsisTextBlock:function(b){var c=this,d=c.element,e=c._viewWidth/2;return c._calcBlockWidth(b)>e&&a(b).width(e-c._marginWidth),b},_modifyInputBoxWidth:function(){var b=this,c=b.element,d=0,e=0,f=0,g=0,h=c.find("div"),i=0,j=0,k=10,l=c.find(".ui-tokentextarea-input");if(c.width()===0)return;b._labelWidth===0&&(b._labelWidth=c.find(".ui-tokentextarea-label").outerWidth(!0),b._anchorWidth=c.find(".ui-tokentextarea-link-base").outerWidth(!0),b._marginWidth=parseInt(a(l).css("margin-left"),10),b._marginWidth+=parseInt(a(l).css("margin-right"),10),b._viewWidth=c.innerWidth()),d=b._marginWidth,e=b._labelWidth,f=b._anchorWidth,g=b._viewWidth-e;for(j=0;j<h.length;j+=1)i=b._calcBlockWidth(h[j]),i>=g+f?i>=g?g=b._viewWidth-i:g=b._viewWidth:i>g?g=b._viewWidth-i:g-=i;g-=d,g<f*2&&(g=b._viewWidth-d),a(l).width(g-f-k)},_stringFormat:function(a){var b=null,c=a,d=0;for(d=1;d<arguments.length;d+=1)b="{"+(d-1)+"}",c=c.replace(b,arguments[d]);return c},_resizeBlocks:function(){var b=this,c=b.element,d=c.find("div"),e=0;for(e=0;e<d.length;e+=1)a(d[e]).css("width","auto"),d[e]=b._ellipsisTextBlock(d[e])},focusIn:function(){if(this._focusStatus==="focusIn")return;var a=this.element;a.find(".ui-tokentextarea-label").attr("tabindex",0).show(),a.find(".ui-tokentextarea-desclabel").remove(),a.find("div.ui-tokentextarea-sblock").removeClass("ui-tokentextarea-sblock").addClass("ui-tokentextarea-block"),a.find("div").attr({"aria-label":"double tap to edit",tabindex:0}).show(),a.find(".ui-tokentextarea-input").removeClass("ui-tokentextarea-input-invisible").addClass("ui-tokentextarea-input-visible").attr("tabindex",0),a.find("a").attr("tabindex",0).show(),this._modifyInputBoxWidth(),this._focusStatus="focusIn",a.removeClass("ui-tokentextarea-focusout").addClass("ui-tokentextarea-focusin").removeAttr("tabindex"),a.find(".ui-tokentextarea-input").focus()},focusOut:function(){if(this._focusStatus==="focusOut")return;var b=this,d=b.element,e=null,f=null,g=null,h="",i=0,j=10,k=d.find(".ui-tokentextarea-label"),l=d.find("span"),m=d.find("div"),n=d.outerWidth(!0)-l.outerWidth(!0)-k.outerWidth(!0),o=0;k.removeAttr("tabindex"),d.find(".ui-tokentextarea-input").removeClass("ui-tokentextarea-input-visible").addClass("ui-tokentextarea-input-invisible").removeAttr("tabindex"),d.find("a").removeAttr("tabindex").hide(),m.removeAttr("aria-label").removeAttr("tabindex").hide(),n-=b._reservedWidth;for(i=0;i<m.length;i++){o=a(m[i]).outerWidth(!0);if(n-o<=0){j=i-1;break}a(m[i]).show(),n-=o}j!==m.length&&(h=b._stringFormat(b.options.description,m.length-j-1),e=a(c.createElement("span")),e.addClass("ui-tokentextarea-desclabel").attr({"aria-label":"more, double tap to edit",tabindex:"-1"}),f=a(c.createElement("span")).text(h).attr("aria-hidden","true"),g=a(c.createElement("span")).text(m.length-j-1).attr("aria-label","and").css("visibility","hidden"),e.append(f),e.append(g),a(m[j]).after(e)),this._focusStatus="focusOut",d.removeClass("ui-tokentextarea-focusin").addClass("ui-tokentextarea-focusout").attr("tabindex",0)},inputText:function(a){var b=this.element;return arguments.length===0?b.find(".ui-tokentextarea-input").val():(b.find(".ui-tokentextarea-input").val(a),a)},select:function(b){var c=this.element,d=null,e=null;if(this._focusStatus==="focusOut")return;return arguments.length===0?(d=c.find("div.ui-tokentextarea-sblock"),d?d.text():null):(this._unlockTextBlock(),e=c.find("div"),e.length>b&&(a(e[b]).removeClass("ui-tokentextarea-block").addClass("ui-tokentextarea-sblock"),c.trigger("select")),null)},add:function(a,b){if(this._focusStatus==="focusOut")return;this._addTextBlock(a,b)},remove:function(b){var c=this,d=this.element,e=d.find("div"),f=0,g=null,h=function(){};if(this._focusStatus==="focusOut")return;arguments.length===0?e.fadeOut("fast",function(){e.remove(),c._modifyInputBoxWidth(),c._trigger("clear")}):isNaN(b)||(f=b<e.length?b:e.length-1,a(e[f]).fadeOut("fast",function(){a(e[f]).remove(),c._modifyInputBoxWidth()}),this._eventRemoveCall=!0,d[0].remove&&(g=d[0].remove,d[0].remove=h),d.triggerHandler("remove"),g&&(d[0].remove=g),this._eventRemoveCall=!1)},length:function(){return this.element.find("div").length},refresh:function(){var a=this,b=this.element.innerWidth();b&&a._viewWidth!==b&&(a._viewWidth=b),a._resizeBlocks(),a._modifyInputBoxWidth()},destroy:function(){var a=this.element,b=null,c=function(){};if(this._eventRemoveCall)return;a.find(".ui-tokentextarea-label").remove(),a.find("div").undelegate("click").remove(),a.find("a").remove(),a.find(".ui-tokentextarea-input").unbind("keyup").remove(),this._eventRemoveCall=!0,a[0].remove&&(b=a[0].remove,a[0].remove=c),a.remove(),b&&(a[0].remove=b),this._eventRemoveCall=!1,this._trigger("destroy")}}),a(c).bind("pagecreate create",function(){a(":jqmData(role='tokentextarea')").tokentextarea()}),a(b).bind("resize",function(){a(":jqmData(role='tokentextarea')").tokentextarea("refresh")})}(jQuery,window,document),function(a,b,c){a.tizen.scrollview.prototype.options.handler=!1,a.tizen.scrollview.prototype.options.handlerTheme="s";var d=a.tizen.scrollview.prototype._setOption,e=function(d){var e=d,f='<div class="ui-handler ui-handler-direction-',g='"><div class="ui-handler-track"><div class="ui-handler-handle"><div class="ui-handler-thumb"></div></div></div></div>',h=e.data("scrollview"),i=h.options,j=i.direction,k=a.mobile.getInheritedTheme(h,"s"),l=i.theme||k,m=h.options.direction==="x",n=h._$view,o=h._$clip,p=e.find(".ui-scrollbar"),q=null,r=null,s=0,t=0,u=0,v=0,w=0,x,y=a.support.touch,z=(y?"touchstart":"mousedown")+".handler",A=(y?"touchmove":"mousemove")+".handler",B=(y?"touchend":"mouseup")+".handler",C=(y?" touchleave":" mouseleave")+".handler",D=function(){t=m?o.width():o.height(),s=(m?n.width():n.height())-t,w=t-u-v*2},E=function(a){var b=Math.round((m?a.x:a.y)/s*w);r[0].style[m?"left":"top"]=b+"px"},F=function(){a(b).unbind(".handler"),e.moveData=null,n.trigger("scrollstop")};if(e.find(".ui-handler-handle").length!==0||typeof j!="string")return;q=a([f,j,g].join("")).appendTo(e.addClass(" ui-handler-"+l)),r=e.find(".ui-handler-handle").attr({tabindex:"0","aria-label":m?"Horizontal handler, double tap and move to scroll":"Verticalhandler, double tap and move to scroll"}).hide(),u=m?r.width():r.height(),v=m?parseInt(q.css("right"),10):parseInt(q.css("bottom"),10),a.extend(e,{moveData:null}),r.bind(z,{e:r[0]},function(c){h._stopMScroll();var d=c.data.e,f=y?c.originalEvent.targetTouches[0]:c;d.style.opacity=1,e.moveData={target:d,X:parseInt(d.style.left,10)||0,Y:parseInt(d.style.top,10)||0,pX:f.pageX,pY:f.pageY},D(),n.trigger("scrollstart"),y||c.preventDefault(),a(b).bind(A,function(a){var b=e.moveData,c=b.target,d=0,f=0,g=y?a.originalEvent.targetTouches[0]:a;d=m?b.X+g.pageX-b.pX:b.Y+g.pageY-b.pY,d<0&&(d=0),d>w&&(d=w),f=-Math.round(d/w*s),m?(h._setScrollPosition(f,0),c.style.left=d+"px"):(h._setScrollPosition(0,f),c.style.top=d+"px"),a.preventDefault()}).bind(B+C,function(a){F()})}),n.bind(B,function(a){F()}),e.bind("scrollstart",function(a){if(!h.enableHandler())return;D();if(s<0||t<u){p.is(":hidden")&&p.show();return}p.is(":visible")&&p.hide(),x&&(clearInterval(x),x=c),q.addClass("ui-handler-visible"),r.stop(!0,!0).fadeIn()}).bind("scrollupdate",function(a,b){if(!h.enableHandler()||s<0||t<u)return;E(h.getScrollPosition())}).bind("scrollstop",function(a){if(!h.enableHandler()||s<0||t<u)return;x=setInterval(function(){E(h.getScrollPosition()),h._gesture_timer||(clearInterval(x),x=c)},10),h._handlerTimer&&(clearTimeout(h._handlerTimer),h._handlerTimer=0),h._handlerTimer=setTimeout(function(){h._timerID===0&&e.moveData===null&&(r.stop(!0,!0).css("opacity",1).fadeOut(function(){q.removeClass("ui-handler-visible")}),h._handlerTimer=0)},1e3)}).bind("mousewheel",function(a){q.removeClass("ui-handler-visible"),E(h.getScrollPosition())})};a.extend(a.tizen.scrollview.prototype,{enableHandler:function(a){if(typeof a=="undefined")return this.options.handler;this.options.handler=!!a;var b=this.element;this.options.handler?(b.find(".ui-handler").length===0&&e(b),b.find(".ui-scrollbar").hide(),b.find(".ui-handler").show()):(b.find(".ui-handler").removeClass("ui-handler-visible").hide(),b.find(".ui-scrollbar").show())},_setHandlerTheme:function(a){if(!a)return;var b="ui-handler-"+this.options.handlerTheme,c="ui-handler-"+a;this.element.removeClass(b).addClass(c),this.options.handlerTheme=a},_setOption:function(a,b){switch(a){case"handler":this.enableHandler(b);break;case"handlerTheme":this._setHandlerTheme(b);break;default:d.call(this,a,b)}},_handlerTimer:0}),a(b).delegate(":jqmData(scroll)","scrollviewcreate",function(){var b=a(this);if(b.attr("data-"+a.mobile.ns+"scroll")==="none"||b.attr("data-"+a.mobile.ns+"handler")!=="true")return;b.scrollview("enableHandler","true")})}(jQuery,document),function(a,b,c){a.widget("tizen.progress",a.mobile.widget,{options:{style:"circle",running:!1},show:function(){a(this.element).show()},hide:function(){a(this.element).hide()},_start:function(){this.init||(a(this.element).append(this.html),this.init=!0),this.show(),a(this.element).find(".ui-progress-"+this.options.style).addClass(this.runningClass)},_stop:function(){a(this.element).find(".ui-progress-"+this.options.style).removeClass(this.runningClass)},running:function(a){if(a===c)return this.options.running;this._setOption("running",a)},_setOption:function(a,c){if(a==="running"){if(typeof c!="boolean"){b.alert("running value MUST be boolean type!");return}this.options.running=c,this._refresh()}},_refresh:function(){this.options.running?this._start():this._stop()},_create:function(){var b=this,c=this.element,d=c.jqmData("style"),e,f;d?this.options.style=d:d=this.options.style,d=="circle"?(a(this.element).addClass("ui-progress-container-circle"),e='<div class="ui-progress-circle"></div>'):d==="pending"&&(a(this.element).addClass("ui-progressbar"),e='<div class="ui-progressbar-bg"><div class="ui-progress-pending"></div></div>'),this.html=a(e),f="ui-progress-"+d+"-running",a.extend(this,{init:!1,runningClass:f}),d==="pending"&&(a(this.element).append(this.html),this.init=!0),this._refresh()}}),a(document).bind("pagecreate create",function(b){a(b.target).find(":jqmData(role='progress')").progress()})}(jQuery,this),function(a,b){a.widget("tizen.triangle",a.tizen.widgetex,{options:{extraClass:"",offset:null,color:null,location:"top",initSelector:":jqmData(role='triangle')"},_create:function(){var b=a("<div></div>",{"class":"ui-triangle"});a.extend(this,{_triangle:b}),this.element.addClass("ui-triangle-container").append(b)},_doCSS:function(){var b=this.options.location||"top",c=a.inArray(b,["top","bottom"])===-1?"top":"left",d={"border-bottom-color":"top"===b?this.options.color:"transparent","border-top-color":"bottom"===b?this.options.color:"transparent","border-left-color":"right"===b?this.options.color:"transparent","border-right-color":"left"===b?this.options.color:"transparent"};d[c]=this.options.offset,this._triangle.removeAttr("style").css(d)},_setOffset:function(b){this.options.offset=b,this.element.attr("data-"+(a.mobile.ns||"")+"offset",b),this._doCSS()},_setExtraClass:function(b){this._triangle.addClass(b),this.options.extraClass=b,this.element.attr("data-"+(a.mobile.ns||"")+"extra-class",b)},_setColor:function(b){this.options.color=b,this.element.attr("data-"+(a.mobile.ns||"")+"color",b),this._doCSS()},_setLocation:function(b){this.element.removeClass("ui-triangle-container-"+this.options.location).addClass("ui-triangle-container-"+b),this._triangle.removeClass("ui-triangle-"+this.options.location).addClass("ui-triangle-"+b),this.options.location=b,this.element.attr("data-"+(a.mobile.ns||"")+"location",b),this._doCSS()}}),a(document).bind("pagecreate create",function(b){a(a.tizen.triangle.prototype.options.initSelector,b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").triangle()})}(jQuery),function(a,b,c,d){function f(a,b){a.tizen||(a.tizen={}),a.tizen.frameworkData=b.frameworkData,a.tizen.loadCustomGlobalizeCulture=b.loadCustomGlobalizeCulture,a.tizen.loadTheme=b.loadTheme,a.tizen.__tizen__=b}var e={libFileName:"tizen-web-ui-fw(.min)?.js",frameworkData:{rootDir:"/usr/lib/tizen-web-ui-fw",version:"0.1",theme:"tizen-white",viewportWidth:"device-width",viewportScale:!1,defaultFontSize:22,minified:!1,debug:!1},log:{debug:function(a){e.frameworkData.debug&&console.log(a)},warn:function(a){console.warn(a)},error:function(a){console.error(a)},alert:function(a){c.alert(a)}},util:{loadScriptSync:function(b,c,d){a.ajax({url:b,dataType:"script",async:!1,crossDomain:!1,success:c,error:function(c,f,g){if(d)d(c,f,g);else{var h=[404],i="Error while loading "+b+"\n"+c.status+":"+c.statusText;-1==a.inArray(c.status,h)?e.log.alert(i):e.log.warn(i)}}})},isMobileBrowser:function(){var a=c.navigator.appVersion.indexOf("Mobile"),b=-1<a;return b}},css:{cacheBust:document.location.href.match(/debug=true/)?"?cacheBust="+(new Date).getTime():"",addElementToHead:function(b){var c=document.getElementsByTagName("head")[0];c&&a(c).prepend(b)},makeLink:function(a){var b=document.createElement("link");return b.setAttribute("rel","stylesheet"),b.setAttribute("href",a),b.setAttribute("name","tizen-theme"),b},load:function(a){var b=document.getElementsByTagName("head")[0],c=b.getElementsByTagName("link"),d,f=null;for(d=0;d<c.length;d++){if(c[d].getAttribute("rel")!="stylesheet")continue;if(c[d].getAttribute("name")=="tizen-theme"||c[d].getAttribute("href")==a){f=c[d];break}}f?f.getAttribute("href")==a?e.log.warn("Theme is already loaded. Skip theme loading in the framework."):f.setAttribute("href",a):this.addElementToHead(this.makeLink(a))}},getParams:function(){function j(){var a=navigator.theme?navigator.theme.split(":")[0]:null;return a&&(a=a.replace("-hd",""),a.match(/^tizen-/)||(a="tizen-"+a)),a}var a=document.getElementsByTagName("script"),b=null,c=!1,e,f,g,h,i;for(e in a){f=a[e],g=f.src?f.getAttribute("src"):d;if(g&&g.match(this.libFileName)){h=g.split(/[\/\\]/),i=-3,this.frameworkData.rootDir=(f.getAttribute("data-framework-root")||h.slice(0,h.length+i).join("/")||this.frameworkData.rootDir).replace(/^file:(\/\/)?/,""),this.frameworkData.version=f.getAttribute("data-framework-version")||h[h.length+i]||this.frameworkData.version,this.frameworkData.theme=f.getAttribute("data-framework-theme")||j()||this.frameworkData.theme,this.frameworkData.viewportWidth=f.getAttribute("data-framework-viewport-width")||this.frameworkData.viewportWidth,this.frameworkData.viewportScale="true"===f.getAttribute("data-framework-viewport-scale")?!0:this.frameworkData.viewportScale,this.frameworkData.minified=g.search(/\.min\.js$/)>-1?!0:!1,this.frameworkData.debug="true"===f.getAttribute("data-framework-debug")?!0:this.frameworkData.debug,c=!0;break}}return c},loadTheme:function(a){var b,c,d;a||(a=e.frameworkData.theme),b=e.frameworkData.rootDir+"/"+e.frameworkData.version+"/themes/"+a,d=b+"/theme.js",e.frameworkData.minified?c=b+"/tizen-web-ui-fw-theme.min.css":c=b+"/tizen-web-ui-fw-theme.css",e.css.load(c),e.util.loadScriptSync(d)},loadGlobalizeCulture:function(b,d){function j(b){var d=b||a("html").attr("lang")||c.navigator.language.split(".")[0]||c.navigator.userLanguage||"en",e=null,f=d.lastIndexOf("-"),g=["Cyrl","Latn","Mong"];return f!=-1&&(e=d.substr(f+1),g.join("-").indexOf(e)<0&&(d=[d.substr(0,f),e.toUpperCase()].join("-"))),d=d=="en"?"en-US":d,d}function k(a){var b=a.lastIndexOf("-"),c;return b!=-1&&(c=a.substr(0,b)),c}function l(a,b){var c=null;return"string"!=typeof a?null:(b&&b[a]?c=b[a]:c=[f.frameworkData.rootDir,f.frameworkData.version,"js","cultures",["globalize.culture.",a,".js"].join("")].join("/"),c)}function m(a,b){e.log.error("Error "+b.status+": "+b.statusText+"::Culture file ("+a+") is failed to load.")}function n(b,c){function d(){e.log.debug("Culture file ("+b+") is loaded successfully.")}function f(a,d,e){c?c(a,d,e):m(b,a)}b?a.ajax({url:b,dataType:"script",cache:!0,async:!1,success:d,error:f}):(i={status:404,statusText:"Not Found"},f(i,null,null))}var f=this,g,h,i;return h=j(b),g=l(h,d),n(g,function(a,b,c){if(a.status==404){var e=k(h),f=l(e,d);n(f,null)}else m(g,a)}),h},setGlobalize:function(){var a=this.loadGlobalizeCulture();b.culture(a)},loadCustomGlobalizeCulture:function(a){e.loadGlobalizeCulture(null,a)},setViewport:function(b){var c=null,d,f;return a("meta[name=viewport]").each(function(){c=this;return}),c?(f=a(c).prop("content"),b=f.replace(/.*width=(device-width|\d+)\s*,?.*$/gi,"$1"),e.log.warn("Viewport is set to '"+b+"' in a meta tag. Framework skips viewport setting.")):(c=document.createElement("meta"),c&&(c.name="viewport",f="width="+b+", user-scalable=no",!!isNaN(b),c.content=f,e.log.debug(f),d=document.getElementsByTagName("head").item(0),d.insertBefore(c,d.firstChild))),b},scaleBaseFontSize:function(b,c){e.log.debug("themedefaultfont size: "+b+", ratio: "+c);var d=Math.max(Math.floor(b*c),4);a("html").css({"font-size":d+"px"}),e.log.debug("html:font size is set to "+d),a(document).ready(function(){a(".ui-mobile").children("body").css({"font-size":d+"px"})})},setScaling:function(){var b=this.frameworkData.viewportWidth,d=this.frameworkData.defaultFontSize,f=1;a("body").attr("data-tizen-theme-default-font-size",d);if(!e.util.isMobileBrowser())return;this.frameworkData.viewportScale==1&&(b="screen-width"),"screen-width"==b&&(c.self==c.top?b=c.outerWidth:b=document.documentElement.clientWidth),b=this.setViewport(b),b!="device-width"&&(f=parseFloat(b/this.frameworkData.defaultViewportWidth),this.scaleBaseFontSize(d,f))}};f(a,e),e.getParams(),e.loadTheme(),e.setScaling(),e.setGlobalize(),a.mobile.autoInitializePage=!1,a(document).ready(function(){a.mobile.initializePage()})}(jQuery,window.Globalize,window),function(a,b,c){a.widget("tizen.progressbar",a.mobile.widget,{options:{value:0,max:100},min:0,_create:function(){this.element.addClass("ui-progressbar").attr({role:"progressbar","aria-valuemin":this.min,"aria-valuemax":this.options.max,"aria-valuenow":this._value()}),this.valueDiv=a("<div class='ui-progressbar-value'></div>").appendTo(this.element),this.valueDiv.wrap("<div class='ui-progressbar-bg'></div>"),this.oldValue=this._value(),this._refreshValue()},_destroy:function(){this.element.removeClass("ui-progressbar").removeAttr("role").removeAttr("aria-valuemin").removeAttr("aria-valuemax").removeAttr("aria-valuenow"),this.valueDiv.remove()},value:function(a){return a===c?this._value():(this._setOption("value",a),this)},_setOption:function(a,b){a==="value"&&(this.options.value=b,this._refreshValue(),this._value()===this.options.max&&this.element.trigger("complete"))},_value:function(){var a=this.options.value;return typeof a!="number"&&(a=0),Math.min(this.options.max,Math.max(this.min,a))},_percentage:function(){return 100*this._value()/this.options.max},_refreshValue:function(){var a=this.value(),b=this._percentage();this.oldValue!==a&&(this.oldValue=a,this.element.trigger("change")),this.valueDiv.toggle(a>this.min).width(b.toFixed(0)+"%"),this.element.attr("aria-valuenow",a)}}),a(document).bind("pagecreate",function(b){a(b.target).find(":jqmData(role='progressbar')").progressbar()})}(jQuery,this),function(a,b){a.widget("mobile.pagelayout",a.mobile.widget,{options:{visibleOnPageShow:!0,disablePageZoom:!0,transition:"slide",fullscreen:!1,tapToggle:!0,tapToggleBlacklist:"a, input, select, textarea, .ui-header-fixed, .ui-footer-fixed",hideDuringFocus:"input, textarea, select",updatePagePadding:!0,supportBlacklist:function(){var a=window,c=navigator.userAgent,d=navigator.platform,e=c.match(/AppleWebKit\/([0-9]+)/),f=!!e&&e[1],g=c.match(/Fennec\/([0-9]+)/),h=!!g&&g[1],i=c.match(/Opera Mobi\/([0-9]+)/),j=!!i&&i[1];return(d.indexOf("iPhone")>-1||d.indexOf("iPad")>-1||d.indexOf("iPod")>-1)&&f&&f<534||a.operamini&&{}.toString.call(a.operamini)==="[object OperaMini]"||i&&j<7458||c.indexOf("Android")>-1&&f&&f<533||h&&h<6||window.palmGetResource!==b&&f&&f<534||c.indexOf("MeeGo")>-1&&c.indexOf("NokiaBrowser/8.5.0")>-1?!0:!1},initSelector:":jqmData(role='content')"},_create:function(){var a=this,b=a.options,c=a.element;if(b.supportBlacklist()){a.destroy();return}a._addFixedClass(),a._addTransitionClass(),a._bindPageEvents(),a._bindContentControlEvents(),a._backBtnQueue=[]},_addFixedClass:function(){var a=this,b=a.options,c=a.element,d=c.siblings(":jqmData(role='header')"),e=c.siblings(":jqmData(role='footer')"),f=c.closest(".ui-page");d.addClass("ui-header-fixed"),e.addClass("ui-footer-fixed"),b.fullscreen?(d.addClass("ui-header-fullscreen"),e.addClass("ui-footer-fullscreen"),f.addClass("ui-page-header-fullscreen").addClass("ui-page-footer-fullscreen")):f.addClass("ui-page-header-fixed").addClass("ui-page-footer-fixed")},_addTransitionClass:function(){var a=this.options.transition;a&&a!=="none"&&(a==="slide"&&(a=this.element.is(".ui-header")?"slidedown":"slideup"),this.element.addClass(a))},setHeaderFooter:function(b){var c=a(b),d=c.find(":jqmData(role='header')").length?c.find(":jqmData(role='header')"):c.siblings(":jqmData(role='header')"),e=c.find(".ui-content"),f=c.find(":jqmData(role='footer')"),g=f.find(":jqmData(role='fieldcontain')"),h=f.find(".ui-controlgroup");c.is(".ui-dialog")||(d.jqmData("position")=="fixed"||a.support.scrollview&&a.tizen.frameworkData.theme.match(/tizen/)?d.css("position","fixed").css("top","0px"):!a.support.scrollview&&d.jqmData("position")!="fixed"&&d.css("position","relative")),d.find("span.ui-title-text-sub").length&&d.addClass("ui-title-multiline"),g.find("div").is(".ui-controlgroup-label")&&g.find("div.ui-controlgroup-label").remove();if(h.length){var i=100/h.find("a").length;h.find("a").each(function(
+a){h.find("a").eq(a).width(i+"%")})}},_bindPageEvents:function(){var b=this,c=b.options,d=b.element,e;d.closest(".ui-page").bind("pagebeforeshow",function(d){var e=this;c.disablePageZoom&&a.mobile.zoom.disable(!0),c.visibleOnPageShow||b.hide(!0),b.setHeaderFooter(e),b._setContentMinHeight(e)}).bind("webkitAnimationStart animationstart updatelayout",function(a,d){var e=this;c.updatePagePadding&&(b.updatePagePadding(e),b.updatePageLayout(e,d))}).bind("pageshow",function(d){var e=this;b._setContentMinHeight(e),b.updatePagePadding(e),b._updateHeaderArea(e),c.updatePagePadding&&a(window).bind("throttledresize."+b.widgetName,function(){b.updatePagePadding(e),b.updatePageLayout(e,!1),b._updateHeaderArea(e),b._setContentMinHeight(e)})}).bind("pagebeforehide",function(d,e){c.disablePageZoom&&a.mobile.zoom.enable(!0),c.updatePagePadding&&a(window).unbind("throttledresize."+b.widgetName)}),window.addEventListener("softkeyboardchange",function(c){var d=a("<div class='ui-btn-footer-down'></div>"),e=a(".ui-page-active"),f,g="footer";e.data("addBackBtn")&&(e.data("addBackBtn")=="header"?g="header":g="footer",c.state=="on"?(e.find(".ui-"+g+" .ui-btn-footer-down").length||d.buttonMarkup({icon:"down"}).appendTo(e.find(".ui-"+g)),f=a(".ui-page-active .ui-btn-back"),f.hide(),b._backBtnQueue.push(f)):c.state=="off"&&(b._backBtnQueue.forEach(function(a){a.show()}),b._backBtnQueue.length=0,a(".ui-btn-footer-down").remove()))})},_bindContentControlEvents:function(){var a=this,b=a.options,c=a.element;c.closest(".ui-page").bind("pagebeforeshow",function(a){})},_setContentMinHeight:function(b){var c=a(b),d=c.find(":jqmData(role='header')"),e=c.find(":jqmData(role='footer')"),f=c.find(":jqmData(role='content')"),g,h=1,i=window.innerHeight;!a.support.scrollview||a.support.scrollview&&f.jqmData("scroll")==="none"?(h=window.outerWidth/window.innerWidth,i=Math.floor(window.outerHeight/h)):i=window.innerHeight,g=i-d.height()-e.height(),a.support.scrollview&&f.jqmData("scroll")!=="none"&&(f.css("min-height",g-parseFloat(f.css("padding-top"))-parseFloat(f.css("padding-bottom"))+"px"),f.children(".ui-scrollview-view").css("min-height",f.css("min-height")))},_updateHeaderArea:function(b){var c=a(b),d=c.find(":jqmData(role='header')").length?c.find(":jqmData(role='header')"):c.siblings(":jqmData(role='header')"),e=d.children("a").length,f=d.children("img").length;c.is(".ui-dialog")||d.find("h1").css("width",window.innerWidth-parseInt(d.find("h1").css("margin-left"),10)*2-d.children("a").width()*e-d.children("a").width()/4-d.children("img").width()*f*4)},_visible:!0,updatePagePadding:function(b){var c=this.element,d=c.siblings(".ui-header").length,e=c.siblings(".ui-footer").length;if(this.options.fullscreen)return;b=b||c.closest(".ui-page"),(c.siblings(".ui-header").jqmData("position")=="fixed"||a.support.scrollview&&c.jqmData("scroll")!=="none")&&a(b).css("padding-top",d?c.siblings(".ui-header").outerHeight():0),a(b).css("padding-bottom",e?c.siblings(".ui-footer").outerHeight():0)},updatePageLayout:function(b,c){var d,e=a(b),f=e.find(":jqmData(role='header')"),g=e.find(":jqmData(role='content')"),h=0,i=0,j=0,k=window.innerHeight,l=1;e.length?d=e.find(":jqmData(role='footer')"):d=a(document).find(":jqmData(role='footer')").eq(0),i=d.css("display")=="none"||d.length==0?0:d.height(),j=f.css("display")=="none"||f.length==0?0:f.height(),i!=0&&d.css("bottom",0),!a.support.scrollview||a.support.scrollview&&g.jqmData("scroll")==="none"?(l=window.outerWidth/window.innerWidth,k=Math.floor(window.outerHeight/l)):k=window.innerHeight,h=k-i-j,a.support.scrollview&&g.jqmData("scroll")!=="none"&&g.height(h-parseFloat(g.css("padding-top"))-parseFloat(g.css("padding-bottom"))),c&&e.css("min-height",h).css("padding-top",j).css("padding-bottom",i)},show:function(a){},hide:function(a){},toggle:function(){this[this._visible?"hide":"show"]()},destroy:function(){this.element.removeClass("ui-header-fixed ui-footer-fixed ui-header-fullscreen ui-footer-fullscreen in out fade slidedown slideup ui-fixed-hidden"),this.element.closest(".ui-page").removeClass("ui-page-header-fixed ui-page-footer-fixed ui-page-header-fullscreen ui-page-footer-fullscreen")},refresh:function(){var b=a(".ui-page-active");this.setHeaderFooter(b),this._updateHeaderArea(b)}}),a(document).bind("pagecreate create",function(b){a(b.target).jqmData("fullscreen")&&a(a.mobile.pagelayout.prototype.options.initSelector,b.target).not(":jqmData(fullscreen)").jqmData("fullscreen",!0),a.mobile.pagelayout.prototype.enhanceWithin(b.target)})}(jQuery),function(a,b,c){a.widget("tizen.tizenslider",a.mobile.widget,{options:{popup:!0},popup:null,handle:null,handleText:null,_create:function(){this.currentValue=null,this.popupVisible=!1;var b=this,d=a(this.element),e,f,g,h,i,j,k,l,m,n,o;d.slider(),d.hide(),b.popup=a('<div class="ui-slider-popup"></div>'),g=d.jqmData("popup"),g!==c&&(b.options.popup=g==1),e=d.next(".ui-slider"),h=d.attr("data-icon"),e.wrap('<div class="ui-slider-container"></div>'),b.handle=e.find(".ui-slider-handle"),e.removeClass("ui-btn-corner-all"),e.find("*").removeClass("ui-btn-corner-all");switch(h){case"bright":case"volume":l=a('<div class="ui-slider-left-'+h+'"></div>'),m=a('<div class="ui-slider-right-'+h+'"></div>'),e.before(l),e.after(m),n=l.width()+16,o=m.width()+16;break;case"text":j=d.attr("data-text-left")===c?"":d.attr("data-text-left").substring(0,3),i=d.attr("data-text-right")===c?"":d.attr("data-text-right").substring(0,3),k=Math.max(j.length,i.length)+1,n=k+"rem",o=k+"rem",l=a('<div class="ui-slider-left-text" style="left:'+ -k+"rem; width:"+k+'rem;">'+'<span style="position:relative;top:0.4em;">'+j+"</span></div>"),m=a('<div class="ui-slider-right-text" style="right:'+ -k+"rem; width:"+k+'rem;">'+'<span style="position:relative;top:0.4em;">'+i+"</span></div>"),e.before(l),e.after(m)}h&&e.parent(".ui-slider-container").css({"margin-left":n,"margin-right":o}),e.append(a('<div class="ui-slider-handle-press"></div>')),b.handle_press=e.find(".ui-slider-handle-press"),b.handle_press.css("display","none"),e.parents(".ui-page").append(b.popup),b.popup.hide(),b.handleText=e.find(".ui-btn-text"),b.updateSlider(),this.element.bind("change",function(){b.updateSlider()}),b.handle.bind("vmousedown",function(){b.showPopup()}),e.add(document).bind("vmouseup",function(){b.hidePopup()})},_handle_press_show:function(){this.handle_press.css("display","")},_handle_press_hide:function(){this.handle_press.css("display","none")},positionPopup:function(){var a=this.handle.offset();this.popup.offset({left:a.left+(this.handle.width()-this.popup.width())/2,top:a.top-this.popup.height()}),this.handle_press.offset({left:a.left,top:a.top})},updateSlider:function(){var a,b,c,d,e,f=function(a){var b=Math.abs(a),c;return b>999?c=4:b>99?c=3:b>9?c=2:c=1,a<0&&c++,c};this.handle.removeAttr("title"),e=this.element.val(),b=f(e);if(this.popupVisible){this.positionPopup();switch(b){case 1:case 2:a="1.5rem",d="0.15rem";break;case 3:a="1rem",d="0.5rem";break;default:a="0.8rem",d="0.5rem"}this.popup.css({"font-size":a,"padding-top":d})}if(e===this.currentValue)return;switch(b){case 1:a="0.95rem",c="0";break;case 2:a="0.85rem",c="-0.01rem";break;case 3:a="0.65rem",c="-0.05rem";break;default:a="0.45rem",c="-0.15rem"}a!=this.handleText.css("font-size")&&this.handleText.css({"font-size":a,top:c}),this.currentValue=e,this.handleText.text(e),this.popup.html(e),this.element.trigger("update",e)},showPopup:function(){if(!this.options.popup||this.popupVisible)return;this.popup.show(),this.popupVisible=!0,this._handle_press_show()},hidePopup:function(){if(!this.options.popup||!this.popupVisible)return;this.popup.hide(),this.popupVisible=!1,this._handle_press_hide()},_setOption:function(a,b){var c=b!==this.options[a];if(!c)return;switch(a){case"popup":this.options.popup=b,this.options.popup?this.updateSlider():this.hidePopup()}}}),a(document).bind("pagebeforecreate",function(d){a.data(b,"jqmSliderInitSelector")===c&&(a.data(b,"jqmSliderInitSelector",a.mobile.slider.prototype.options.initSelector),a.mobile.slider.prototype.options.initSelector=null)}),a(document).bind("pagecreate create",function(c){var d=a.data(b,"jqmSliderInitSelector");a(c.target).find(d).each(function(){var b=a(this);b.is("select")?b.slider():b.tizenslider()})})}(jQuery,this),function(a){a.widget("tizen.swipe",a.mobile.widget,{options:{theme:null},_create:function(){var a=this.element.jqmData("theme")||this.options.theme||this.element.parent().jqmData("theme")||"s";this.options.theme=a,this._isopen=!1,this.refresh()},refresh:function(){this._cleanupDom();var b=this,c,d,e,f,g;c="ui-body-"+this.options.theme,this.element.parent().hasClass("ui-listview")||this.element.parent().listview(),this.element.addClass("ui-swipe"),d=this.element.find(':jqmData(role="swipe-item-cover")'),f=this.element.find(':jqmData(role="swipe-item")'),this._covers=d,this._item=f,f.addClass("ui-swipe-item"),e=c,g=f.parent().attr("class").match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/),d.each(function(){var c=a(this);g&&(e=g[0]),c.addClass("ui-swipe-item-cover"),c.addClass(e),c.has(".ui-swipe-item-cover-inner").length===0&&c.wrapInner(a("<span/>").addClass("ui-swipe-item-cover-inner"));if(!c.data("animateRight")||!c.data("animateLeft"))c.data("animateRight",function(){b._animateCover(c,110,f)}),c.data("animateLeft",function(){b._animateCover(c,0,f)});f.bind("swipeleft",c.data("animateLeft")),c.bind("swiperight",c.data("animateRight")),f.find(".ui-btn").bind("vclick",c.data("animateLeft"))})},_cleanupDom:function(){var a=this,b,c,d=b,e,f,g,h,i;b="ui-body-"+this.options.theme,this.element.removeClass("ui-swipe"),c=this.element.find(':jqmData(role="swipe-item-cover")'),e=this.element.find(':jqmData(role="swipe-item")'),e.removeClass("ui-swipe-item"),c.removeClass("ui-swipe-item-cover"),f=e.attr("class"),g=f&&f.match(/ui\-body\-[a-z]|ui\-bar\-[a-z]/),g&&(d=g[0]),c.removeClass(d),i=c.find(".ui-swipe-item-cover-inner"),i.children().unwrap(),h=i.text(),h&&(c.append(h),i.remove()),c.data("animateRight")&&c.data("animateLeft")&&(c.unbind("swiperight",c.data("animateRight")),e.unbind("swipeleft",c.data("animateLeft")),e.find(".ui-btn").unbind("vclick",c.data("animateLeft")),c.data("animateRight",null),c.data("animateLeft",null))},_animateCover:function(b,c,d){var e=this,f={easing:"linear",duration:"normal",queue:!0,complete:function(){b.trigger("animationend")}};a(this.element.parent()).find(":jqmData(role='swipe')").each(function(){this!==e.element.get(0)&&a(this).swipe("opened")&&a(this).swipe("close")}),c==110?this._isopen=!0:this._isopen=!1,b.stop(),b.clearQueue(),b.trigger("animationstart"),b.animate({left:c+"%"},f),c==0?d.animate({opacity:0},"slow"):d.animate({opacity:1},"slow")},destroy:function(){this._cleanupDom()},open:function(){var b=this;a(b._covers).each(function(){var c=a(this);b._animateCover(c,110,b._item)})},opened:function(){return this._isopen},close:function(){var b=this;a(b._covers).each(function(){var c=a(this);b._animateCover(c,0,b._item)})}}),a(document).bind("pagecreate",function(b){a(b.target).find(":jqmData(role='swipe')").swipe()})}(jQuery),function(a,b){a.widget("tizen.notification",a.mobile.widget,{btn:null,text_bg:[],icon_img:[],interval:null,seconds:null,running:!1,_get_text:function(){var b=new Array(2);return this.type==="ticker"?(b[0]=a(this.text_bg[0]).text(),b[1]=a(this.text_bg[1]).text()):b[0]=a(this.text_bg[0]).text(),b},_set_text:function(b,c){var d=function(a,b){if(!b)return;a.text(b)};this.type==="ticker"?(d(a(this.text_bg[0]),b),d(a(this.text_bg[1]),c)):d(a(this.text_bg[0]),b)},text:function(a,b){if(a===undefined&&b===undefined)return this._get_text();this._set_text(a,b)},icon:function(b){if(b===undefined)return;this.icon_img.detach(),this.icon_img=a("<img src='"+b+"' class='ui-ticker-icon'>"),a(this.element).find(".ui-ticker").append(this.icon_img)},_refresh:function(){var b=this._get_container();a(b).addClass("fix").removeClass("show").removeClass("hide"),this._set_interval()},open:function(){var b=this._get_container();if(this.running){this._refresh();return}a(b).addClass("show").removeClass("hide").removeClass("fix"),this.running=!0,this.type==="popup"&&this._set_position(),this._set_interval()},close:function(){var b=this._get_container();if(!this.running)return;a(b).addClass("hide").removeClass("show").removeClass("fix"),this.running=!1,clearInterval(this.interval)},destroy:function(){var b=this._get_container();a(b).removeClass("show").removeClass("hide").removeClass("fix"),this._del_event(),this.running=!1},_get_container:function(){return this.type==="ticker"?a(this.element).find(".ui-ticker"):a(this.element).find(".ui-smallpopup")},_set_interval:function(){var a=this;clearInterval(this.interval),this.seconds!==undefined&&this.second!==0&&(this.interval=setInterval(function(){a.close()},this.seconds))},_add_event:function(){var a=this,b=this._get_container();this.type==="ticker"&&(b.find(".ui-ticker-btn").append(this.btn).trigger("create"),this.btn.bind("vmouseup",function(){a.close()})),b.bind("vmouseup",function(){a.close()})},_del_event:function(){var a=this._get_container();this.type==="ticker"&&this.btn.unbind("vmouseup"),a.unbind("vmouseup"),clearInterval(this.interval)},_set_position:function(){var b=this._get_container(),c=a(".ui-page-active").children(".ui-footer"),d=c.outerHeight()||0;b.css("bottom",d)},_create:function(){var c=this,d=a(this.element),e;this.btn=a('<div data-role="button" data-inline="true">Close</div>'),this.seconds=d.jqmData("interval"),this.type=d.jqmData("type")||"popup";if(this.type==="ticker"){d.wrapInner("<div class='ui-ticker'></div>"),d.find(".ui-ticker").append("<div class='ui-ticker-body'></div><div class='ui-ticker-btn'></div>"),this.text_bg=d.find("p");if(this.text_bg.length<2)d.find(".ui-ticker").append("<p></p><p></p>"),this.text_bg=d.find("p");else if(this.text_bg.length>2)for(e=2;e<this.text_bg.length;e++)a(this.text_bg[e]).css("display","none");a(this.text_bg[0]).addClass("ui-ticker-text1-bg"),a(this.text_bg[1]).addClass("ui-ticker-text2-bg"),this.icon_img=d.find("img");if(this.icon_img.length){a(this.icon_img).addClass("ui-ticker-icon");for(e=1;e<this.icon_img.length;e++)a(this.icon_img[e]).css("display","none")}}else{d.wrapInner("<div class='ui-smallpopup'></div>"),this.text_bg=d.find("p").addClass("ui-smallpopup-text-bg");if(this.text_bg.length<1)d.find(".ui-smallpopup").append("<p class='ui-smallpopup-text-bg'></p>"),this.text_bg=d.find("p");else if(this.text_bg.length>1)for(e=1;e<this.text_bg.length;e++)a(this.text_bg[e]).css("display","none");this._set_position()}this._add_event(),a(b).bind("resize",function(){if(!c.running)return;c._refresh(),c.type==="popup"&&c._set_position()})}}),a(document).bind("pagecreate create",function(b){a(b.target).find(":jqmData(role='notification')").notification()}),a(document).bind("pagebeforehide",function(b){a(b.target).find(":jqmData(role='notification')").notification("destroy")})}(jQuery,this),function(a,b){a.widget("tizen.popupwindow",a.tizen.widgetex,{options:{theme:null,overlayTheme:"s",style:"custom",disabled:!1,shadow:!0,corners:!0,fade:!1,opacity:.7,widthRatio:.8612,transition:a.mobile.defaultDialogTransition,initSelector:":jqmData(role='popupwindow')"},_htmlProto:{source:["<div><div>"," <div id='popupwindow-screen' class='ui-selectmenu-screen ui-screen-hidden ui-popupwindow-screen'></div>"," <div id='popupwindow-container' class='ui-popupwindow ui-popupwindow-padding ui-selectmenu-hidden ui-overlay-shadow ui-corner-all'></div>","</div>","</div>"].join(""),ui:{screen:"#popupwindow-screen",container:"#popupwindow-container"}},_setStyle:function(){var a=this.element,b=a.attr("data-style");b&&(this.options.style=b),a.addClass(this.options.style),a.find(":jqmData(role='title')").wrapAll("<div class='popup-title'></div>"),a.find(":jqmData(role='text')").wrapAll("<div class='popup-text'></div>"),a.find(":jqmData(role='button-bg')").wrapAll("<div class='popup-button-bg'></div>"),a.find(":jqmData(role='check-bg')").wrapAll("<div class='popup-check-bg'></div>"),a.find(":jqmData(role='scroller-bg')").addClass("popup-scroller-bg"),a.find(":jqmData(role='text-bottom-bg')").wrapAll("<div class='popup-text-bottom-bg'></div>"),a.find(":jqmData(role='text-left')").wrapAll("<div class='popup-text-left'></div>"),a.find(":jqmData(role='text-right')").wrapAll("<div class='popup-text-right'></div>"),a.find(":jqmData(role='progress-bg')").wrapAll("<div class='popup-progress-bg'></div>")},_create:function(){console.warn("popupwindow() was deprecated. use popup() instead.");var b=this.element.closest(":jqmData(role='page')"),c=this;b.length===0&&(b=a("body")),this._ui.placeholder=a("<div><!-- placeholder for "+this.element.attr("id")+" --></div>").css("display","none").insertBefore(this.element),b.append(this._ui.screen),this._ui.container.insertAfter(this._ui.screen),this._ui.container.append(this.element),this._setStyle(),this._isOpen=!1,this._ui.screen.bind("vclick",function(a){return c.close(),!1}),this.element.bind("vclick",function(b){a(b.target).is("ui-btn-ctxpopup-close")&&c.close()})},destroy:function(){this.element.insertBefore(this._ui.placeholder),this._ui.placeholder.remove(),this._ui.container.remove(),this._ui.screen.remove(),this.element.triggerHandler("destroyed"),a.Widget.prototype.destroy.call(this)},_placementCoords:function(b,c,d,e){var f=a(window).height(),g=a(window).width(),h=e/2,i=parseFloat(this._ui.container.css("max-width")),j=c,k=f-c,l,m;return j>e/2&&k>e/2?l=c-h:l=j>k?f-e-30:30,d<i?m=(g-d)/2:(m=b-d/2,m<10?m=10:m+d>g&&(m=g-d-10)),{x:m,y:l}},_setPosition:function(c,d){var e=b===c?a(window).width()/2:c,f=b===d?a(window).height()/2:d,g,h=this.element.data("ctxpopup"),i,j,k,l,m,n,o,p,q,r,s;h||(i=a(window).width()*this.options.widthRatio,this._ui.container.css("width",i),this._ui.container.outerWidth()>a(window).width()&&this._ui.container.css({"max-width":a(window).width()-30})),g=this._placementCoords(e,f,this._ui.container.outerWidth(),this._ui.container.outerHeight()),j=this._ui.container.innerHeight(),k=this._ui.container.innerWidth(),l=a(window).height(),m=a(window).width(),n=f,o=l-f,p=j/2,q=parseFloat(this._ui.container.css("max-width")),r=(l-j)/2,!q||k<q?s=(m-k)/2:(s=e-k/2,s<30?s=30:s+k>m&&(s=m-k-30)),h&&(r=g.y,s=g.x),this._ui.container.css({top:r,left:s}),this._ui.screen.css("height",l)},open:function(b,c,d){var e=this,f=0;if(this._isOpen||this.options.disabled)return;a(document).find("*").each(function(){var b=a(this),c=parseInt(b.css("z-index"),10);b.is(e._ui.container)||b.is(e._ui.screen)||isNaN(c)||(f=Math.max(f,c))}),this._ui.screen.css("height",a(window).height()),d?this._ui.screen.css("opacity",0).removeClass("ui-screen-hidden"):(this._ui.removeClass("ui-screen-hidden"),this.options.fade?this._ui.screen.animate({opacity:this.options.opacity},"fast"):this._ui.screen.css({opacity:this.options.opacity})),this._setPosition(b,c),this.element.trigger("popupbeforeposition"),this._ui.container.removeClass("ui-selectmenu-hidden").addClass("in").animationComplete(function(){e.element.trigger("popupafteropen")}),this._isOpen=!0,this._reflow||(this._reflow=function(){if(!e._isOpen)return;e._setPosition(b,c)},a(window).bind("resize",this._reflow))},close:function(){if(!this._isOpen)return;this._reflow&&(a(window).unbind("resize",this._reflow),this._reflow=null);var b=this,c=function(){b._ui.screen.addClass("ui-screen-hidden"),b._isOpen=!1};this._ui.container.removeClass("in").addClass("reverse out"),this.options.transition==="none"?(this._ui.container.addClass("ui-selectmenu-hidden").removeAttr("style"),this.element.trigger("popupafterclose")):this._ui.container.animationComplete(function(){b._ui.container.removeClass("reverse out").addClass("ui-selectmenu-hidden").removeAttr("style"),b.element.trigger("popupafterclose")}),this.options.fade?this._ui.screen.animate({opacity:0},"fast",c):c()},_realSetTheme:function(a,b){var c=(a.attr("class")||"").split(" "),d=!0,e=null,f;while(c.length>0){e=c.pop(),f=e.match(/^ui-body-([a-z])$/);if(f&&f.length>1){e=f[1];break}e=null}a.removeClass("ui-body-"+e),(b||"").match(/[a-z]/)&&a.addClass("ui-body-"+b)},_setTheme:function(b){this._realSetTheme(this.element,b),this.options.theme=b,this.element.attr("data-"+(a.mobile.ns||"")+"theme",b)},_setOverlayTheme:function(b){this._realSetTheme(this._ui.container,b),this.options.overlayTheme=b,this.element.attr("data-"+(a.mobile.ns||"")+"overlay-theme",b)},_setShadow:function(b){this.options.shadow=b,this.element.attr("data-"+(a.mobile.ns||"")+"shadow",b),this._ui.container[b?"addClass":"removeClass"]("ui-overlay-shadow")},_setCorners:function(b){this.options.corners=b,this.element.attr("data-"+(a.mobile.ns||"")+"corners",b),this._ui.container[b?"addClass":"removeClass"]("ui-corner-all")},_setFade:function(b){this.options.fade=b,this.element.attr("data-"+(a.mobile.ns||"")+"fade",b)},_setTransition:function(b){this._ui.container.removeClass(this.options.transition||"").addClass(b),this.options.transition=b,this.element.attr("data-"+(a.mobile.ns||"")+"transition",b)},_setDisabled:function(b){a.Widget.prototype._setOption.call(this,"disabled",b),b&&this.close()}}),a.tizen.popupwindow.bindPopupToButton=function(a,b){if(a.length===0||b.length===0)return;var c=function(c){return b.jqmData("overlay-theme-set")||b.popupwindow("option","overlayTheme",a.jqmData("theme")),b.popupwindow("open",a.offset().left+a.outerWidth()/2,a.offset().top+a.outerHeight()/2),!1};(b.popupwindow("option","overlayTheme")||"").match(/[a-z]/)&&b.jqmData("overlay-theme-set",!0),a.attr({"aria-haspopup":!0,"aria-owns":a.attr("href")}).removeAttr("href").bind("vclick",c),b.bind("destroyed",function(){a.unbind("vclick",c)})},a(document).bind("pagecreate create",function(b){a(a.tizen.popupwindow.prototype.options.initSelector,b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").popupwindow(),a("a[href^='#']:jqmData(rel='popupwindow')",b.target).each(function(){a.tizen.popupwindow.bindPopupToButton(a(this),a(a(this).attr("href")))})})}(jQuery),function(a,b){a.widget("tizen.searchbar",a.mobile.widget,{options:{theme:null,initSelector:"input[type='search'],:jqmData(type='search'), input[type='tizen-search'],:jqmData(type='tizen-search')"},_create:function(){function t(){setTimeout(function(){h.toggleClass("ui-input-clear-hidden",!c.val())},0)}function u(){g.addClass("ui-input-search-default").removeClass("ui-input-search-wide"),i.addClass("ui-btn-cancel-show").removeClass("ui-btn-cancel-hide")}function v(){g.addClass("ui-input-search-wide").removeClass("ui-input-search-default"),i.addClass("ui-btn-cancel-hide").removeClass("ui-btn-cancel-show"),t()}function w(){var b=a(c).jqmData("icon"),d=a("<div data-role='button' data-style='circle'></div>");d.appendTo(g.parent()).buttonMarkup({icon:b,iconpos:"notext",corners:!0,shadow:!0}),d.addClass("ui-btn-search-front-icon")}var c=this.element,d=this.options,e=d.theme||a.mobile.getInheritedTheme(this.element,"c"),f=" ui-body-"+e,g,h,i,j,k,l,m,n,o,p,q,r=!1,s=!1;a("label[for='"+c.attr("id")+"']").addClass("ui-input-text"),typeof c[0].autocorrect!="undefined"&&!a.support.touchOverflow&&(c[0].setAttribute("autocorrect","off"),c[0].setAttribute("autocomplete","off")),g=c.wrap("<div class='ui-input-search ui-shadow-inset ui-corner-all ui-btn-shadow"+f+"'></div>").parent(),a(this.element).data("cancel-btn")===!0&&(r=!0,g.addClass("ui-input-search-default")),a(this.element).data("icon")!=b&&(s=!0,g.addClass("ui-search-bar-icon")),h=a("<a href='#' class='ui-input-clear' title='clear text'>clear text</a>").bind("click",function(a){if(c.attr("disabled")=="disabled")return!1;c.val("").focus().trigger("change"),h.addClass("ui-input-clear-hidden"),a.preventDefault()}).appendTo(g).buttonMarkup({icon:"deleteSearch",iconpos:"notext",corners:!0,shadow:!0}),t(),c.bind("paste cut keyup focus change blur",t),g.wrapAll("<div class='input-search-bar'></div>"),p=a("<div class='ui-image-search'></div>").appendTo(g),s&&w(),r&&(i=a("<div data-role='button' class='ui-input-cancel' title='clear text'>Cancel</div>").bind("click",function(a){if(c.attr("disabled")=="disabled")return!1;a.preventDefault(),a.stopPropagation(),c.val("").blur().trigger("change"),r&&v()}).appendTo(g.parent()).buttonMarkup({iconpos:"cancel",corners:!0,shadow:!0})),c.focus(function(){if(c.attr("disabled")=="disabled")return!1;r&&u(),g.addClass(a.mobile.focusClass)}).blur(function(){g.removeClass(a.mobile.focusClass)}),j=c.jqmData("default-text"),j!=b&&j.length>0&&(k="ui-input-default-text",l=j.replace(/\s/g,""),m=k+"-"+l,n=a("<style>."+m+":after"+"{content:"+"'"+j+"'"+"}"+"</style>"),a("html > head").append(n),o=a("<div></div>"),o.addClass(k),o.addClass(m),o.tap(function(a){c.blur(),c.focus()}),c.parent().append(o),c.focus(function(){c.parent().find("div.ui-input-default-text").addClass("ui-input-default-hidden")}).blur(function(){var a=c.val();a.length>0?c.parent().find("div.ui-input-default-text").addClass("ui-input-default-hidden"):c.parent().find("div.ui-input-default-text").removeClass("ui-input-default-hidden")})),c.attr("placeholder")||c.attr("placeholder","Search")},disable:function(){this.element.attr("disabled",!0),this.element.parent().addClass("ui-disabled"),a(this.element).blur(),this.element.parent().parent().find(".ui-input-cancel").addClass("ui-disabled")},enable:function(){this.element.attr("disabled",!1),this.element.parent().removeClass("ui-disabled"),this.element.parent().parent().find(".ui-input-cancel").removeClass("ui-disabled"),a(this.element).focus()}}),a(document).bind("pagecreate create",function(b){a.tizen.searchbar.prototype.enhanceWithin(b.target)})}(jQuery),function(a,b){a.widget("tizen.tabbar",a.mobile.widget,{options:{iconpos:"top",grid:null,defaultList:4,initSelector:":jqmData(role='tabbar')"},_create:function(){var c=this.element,d,e,f,g=a.mobile.listview.prototype.options.theme,h=window.innerWidth||a(window).width(),i=window.innerHeight||a(window).height(),j="<div class='ui-tabbar-divider ui-tabbar-divider-left'></div>",k="<div class='ui-tabbar-divider ui-tabbar-divider-right'></div>",l;l=h>i&&h-i,l?c.removeClass("ui-portrait-tabbar").addClass("ui-landscape-tabbar"):c.removeClass("ui-landscape-tabbar").addClass("ui-portrait-tabbar"),c.find("a").length&&(d=c.find("a"),f=d.filter(":jqmData(icon)").length?this.options.iconpos:b,e=d.html().length?!0:!1),c.parents(".ui-header").length&&c.parents(".ui-scrollview-view").length?(c.find("li").addClass("tabbar-scroll-li"),c.find("ul").addClass("tabbar-scroll-ul"),a(j).appendTo(c.parents(".ui-scrollview-clip")),a(k).appendTo(c.parents(".ui-scrollview-clip")),a(".ui-tabbar-divider-left").hide(),a(".ui-tabbar-divider-right").hide(),c.parents(".ui-scrollview-view").data("default-list")&&(this.options.defaultList=c.parents(".ui-scrollview-view").data("default-list")),c.find("li").css("width",window.innerWidth/this.options.defaultList+"px")):c.find("ul").children().length&&c.addClass("ui-navbar").find("ul").grid({grid:this.options.grid}),c.parents(".ui-footer").length&&c.find("li").addClass("ui-tab-btn-style"),c.siblings(".ui-title").length&&c.parents(".ui-header").addClass("ui-title-tabbar"),f||c.addClass("ui-tabbar-noicons"),e||c.addClass("ui-tabbar-notext"),e&&f&&c.parents(".ui-header").addClass("ui-title-tabbar-multiline"),c.find("a").length&&d.buttonMarkup({corners:!1,shadow:!1,iconpos:f}),c.find(".ui-state-persist").length&&c.addClass("ui-tabbar-persist"),c.delegate("a","vclick",function(b){d.not(".ui-state-persist").removeClass(a.mobile.activeBtnClass),a(this).addClass(a.mobile.activeBtnClass)}),c.addClass("ui-tabbar"),a(document).bind("pagebeforeshow",function(b,c){var d=a(b.target).find(":jqmData(role='footer')"),e=d.find(":jqmData(role='tabbar')"),f=e.siblings(":jqmData(icon='naviframe-more')"),g=e.siblings(".ui-btn-back");d.css("position","fixed").css("bottom",0).css("height",e.height()),f.length&&e.addClass("ui-tabbar-margin-more"),g.length&&e.addClass("ui-tabbar-margin-back")}),c.bind("touchstart vmousedown",function(b){var c=a(b.target).parents(".ui-scrollview-view");c.offset()&&(c.offset().left<0?a(".ui-tabbar-divider-left").show():a(".ui-tabbar-divider-left").hide(),c.width()-c.parents(".ui-scrollview-clip").width()==Math.abs(c.offset().left)?a(".ui-tabbar-divider-right").hide():a(".ui-tabbar-divider-right").show())}),this._bindTabbarEvents(),this._initTabbarAnimation()},_initTabbarAnimation:function(){var b=!1,c=!1;a(document).bind("scrollstart.tabbar",function(d){a(d.target).find(".ui-tabbar").length&&(b=!0,c=!1)}),a(document).bind("scrollstop.tabbar",function(d){var e=a(d.target),f=a(d.target).find(".ui-tabbar"),g=a(d.target).find(".ui-tabbar li"),h=g.eq(0),i,j=-1;c=!0,f.length&&b==1&&(i=Math.abs(g.eq(0).offset().left),g.each(function(a){var b=g.eq(a).offset();Math.abs(b.left)<i&&(i=Math.abs(b.left),j=a,h=g.eq(a))}),e.length&&b==c&&j!=-1&&(b=!1,e.scrollview("scrollTo",-(window.innerWidth/f.data("defaultList")*j),0,357))),a(".ui-tabbar-divider-left").hide(),a(".ui-tabbar-divider-right").hide()})},_bindTabbarEvents:function(){var b=this.element;a(window).bind("orientationchange",function(c,d){var e=window.innerWidth||a(window).width(),f=window.innerHeight||a(window).height(),g=e>f&&e-f;g?b.removeClass("ui-portrait-tabbar").addClass("ui-landscape-tabbar"):b.removeClass("ui-landscape-tabbar").addClass("ui-portrait-tabbar")})},_setDisabled:function(a,b){this.element.find("li").eq(b).attr("disabled",a),this.element.find("li").eq(b).attr("aria-disabled",a)},disable:function(a){this._setDisabled(!0,a),this.element.find("li").eq(a).addClass("ui-disabled")},enable:function(a){this._setDisabled(!1,a),this.element.find("li").eq(a).removeClass("ui-disabled")}}),a(document).bind("pagecreate create",function(b){a(a.tizen.tabbar.prototype.options.initSelector,b.target).tabbar()})}(jQuery),function(a,b){a.widget("tizen.ctxpopup",a.tizen.widgetex,{options:a.extend({},a.tizen.popupwindow.prototype.options,{initSelector:":jqmData(show-arrow)"}),_htmlProto:{source:["<div><div id='outer' class='ui-ctxpopup'>"," <div id='top' class='ui-ctxpopup-row' data-role='triangle' data-location='top'></div>"," <div class='ui-ctxpopup-row'>"," <div id='left' class='ui-ctxpopup-cell' data-role='triangle' data-location='left'></div>"," <div id='container' class='ui-ctxpopup-cell'></div>"," <div id='right' class='ui-ctxpopup-cell' data-role='triangle' data-location='right'></div>"," </div>"," <div id='bottom' class='ui-ctxpopup-row' data-role='triangle' data-location='bottom'></div>","</div>","</div>"].join(""),ui:{outer:"#outer",container:"#container",arrow:{all:":jqmData(role='triangle')",l:"#left",t:"#top",r:"#right",b:"#bottom"}}},_create:function(){console.warn("ctxpopup() was deprecated. use popup() instead."),this.element.data("popupwindow")||this.element.popupwindow(),this.element.data("popupwindow")._ui.container.removeClass("ui-popupwindow-padding").append(this._ui.outer),this._ui.outer.trigger("create"),this._ui.container.addClass("ui-popupwindow-padding").append(this.element)},_setOption:function(b,c){a.tizen.popupwindow.prototype._setOption.apply(this.element.data("popupwindow"),arguments),this.options[b]=c}});var c=a.tizen.popupwindow.prototype.open,d=a.tizen.popupwindow.prototype._setOption,e=a.tizen.popupwindow.prototype._placementCoords;a.tizen.popupwindow.prototype._setOption=function(a,b){var c=this.element.data("ctxpopup"),e=!0,f;if(c){if("shadow"===a||"overlayTheme"===a||"corners"===a)f=this._ui.container,this._ui.container=c._ui.container,d.apply(this,arguments),this._ui.container=f,e=!1;c.options[a]=b}e&&d.apply(this,arguments)},a.tizen.popupwindow.prototype._placementCoords=function(c,d,f,g){function m(a,b,f){h._ui.arrow.all.hide(),h._ui.arrow[a].show();var g="b"===a||"t"===a,j=g?{point:"x",size:"cx",beg:"left",outerSize:"outerWidth",niceSize:"width",triangleSize:"height"}:{point:"y",size:"cy",beg:"top",outerSize:"outerHeight",niceSize:"height",triangleSize:"width"},k={cx:i._ui.container.width(),cy:i._ui.container.height()},l={cx:k.cx/2,cy:k.cy/2},m={x:c+l.cx*b,y:d+l.cy*f},n=e.call(i,m.x,m.y,k.cx,k.cy),o=h._ui.arrow[a].offset()[j.beg],p=h._ui.arrow[a][j.outerSize](!0),q=i.element.offset()[j.beg],r=i.element[j.outerSize](!0),s=h._ui.arrow[a][j.triangleSize](),t=Math.max(s+Math.max(0,q-o),Math.min(p-s-Math.max(0,o+p-(q+r)),p/2+m[j.point]-n[j.point]-l[j.size])),u={x:n.x+(g?t:0)+("r"===a?k.cx:0),y:n.y+(g?0:t)+("b"===a?k.cy:0)},v={actual:n,triangleOffset:t,absDiff:Math.abs(c-u.x)+Math.abs(d-u.y)};return h._ui.arrow[a].hide(),v}var h=this.element.data("ctxpopup"),i=this,j={},k,l;return h?(j={l:m("l",1,0),r:m("r",-1,0),t:m("t",0,1),b:m("b",0,-1)},a.each(j,function(a,c){if(k===b||c.absDiff<k)k=c.absDiff,l=a}),h._ui.arrow[l].show().triangle("option","offset",j[l].triangleOffset),j[l].actual):e.call(this,c,d,f,g)},a.tizen.popupwindow.prototype.open=function(b,d){
+var e=this.element.data("ctxpopup");e&&(this._setFade(!1),this._setShadow(!1),this._setCorners(!1),this._setOverlayTheme(null),this._setOption("overlayTheme",e.options.overlayTheme),e._ui.arrow.all.triangle("option","color",e._ui.container.css("background-color")),a(".ui-popupwindow").css("background","none")),c.call(this,b,d,!0)},a(document).bind("pagecreate create",function(b){var c=a(a.tizen.ctxpopup.prototype.options.initSelector,b.target);a.tizen.ctxpopup.prototype.enhanceWithin(b.target)})}(jQuery),function(a,b,c){a.widget("tizen.datetimepicker",a.tizen.widgetex,{options:{type:null,format:null,date:null,initSelector:"input[type='date'], input[type='datetime'], input[type='time'], :jqmData(role='datetimepicker')"},container:null,_calendar:function(){return b.Globalize.culture().calendars.standard},_value:{attr:"data-"+(a.mobile.ns||"")+"date",signal:"date-changed"},_daysInMonth:[31,28,31,30,31,30,31,31,30,31,30,31],_isLeapYear:function(a){return a%4?0:a%100?1:a%400?0:1},_makeTwoDigits:function(a){var b=a.toString(10);return a<10&&(b="0"+b),b},_setType:function(b){switch(b){case"datetime":case"date":case"time":this.options.type=b;break;default:this.options.type="datetime"}return this.element.attr("data-"+(a.mobile.ns?a.mobile.ns+"-":"")+"type",this.options.type),this.options.type},_setFormat:function(b){if(this.options.format==b)return;this.options.format=b,this.ui.children().remove();var c=this._parsePattern(b),d=document.createElement("div"),e,f,g,h,i=this;while(c.length>0){e=c.shift(),f='<span class="ui-datefield-%1" data-pat="'+e+'">%2</span>';switch(e){case"H":case"HH":case"h":case"hh":a(d).append(f.replace("%1","hour"));break;case"mm":case"m":this.options.type=="date"?a(d).append(f.replace("%1","month")):a(d).append(f.replace("%1","min"));break;case"ss":case"s":a(d).append(f.replace("%1","sec"));break;case"d":case"dd":a(d).append(f.replace("%1","day"));break;case"M":case"MM":case"MMM":case"MMMM":a(d).append(f.replace("%1","month"));break;case"yy":case"yyyy":a(d).append(f.replace("%1","year"));break;case"t":case"tt":h='<a href="#" class="ui-datefield-period" data-role="button" data-inline="true">period</a>',a(d).append(h);break;case"g":case"gg":a(d).append(f.replace("%1","era").replace("%2",this._calendar().eras.name));break;case"\t":a(d).append(f.replace("%1","tab").replace("%2",e));break;default:a(d).append(f.replace("%1","seperator").replace("%2",e))}}return this.ui.append(d),this.options.date&&this._setDate(this.options.date),this.ui.find(".ui-datefield-period").buttonMarkup().bind("vclick",function(a){return i._switchAmPm(i),!1}),this.element.attr("data-"+(a.mobile.ns?a.mobile.ns+"-":"")+"format",this.options.format),this.options.format},_setDate:function(b){function i(){return b.getMonth()+1}typeof b=="string"&&(b=new Date(b));var c=a("span,a",this.ui),d,e,f,g,h;for(h=0;h<c.length;h++){f=a(c[h]),d=f.attr("class").match(/ui-datefield-([\w]*)/),d||(d="");switch(d[1]){case"hour":e=b.getHours;break;case"min":e=b.getMinutes;break;case"sec":e=b.getSeconds;break;case"year":e=b.getFullYear;break;case"month":e=i;break;case"day":e=b.getDate;break;case"period":e=b.getHours()<12?this._calendar().AM[0]:this._calendar().PM[0],g=f.find(".ui-btn-text"),g.length==0?f.text(e):g.text()!=e&&g.text(e),e=null;break;default:e=null}e&&this._updateField(f,e.call(b))}return this.options.date=b,this._setValue(b),this.element.attr("data-"+(a.mobile.ns?a.mobile.ns+"-":"")+"date",this.options.date),this.options.date},destroy:function(){this.ui&&this.ui.remove(),this.element&&this.element.show()},value:function(a){function b(a,b){return b._makeTwoDigits(a.getHours())+":"+b._makeTwoDigits(a.getMinutes())+":"+b._makeTwoDigits(a.getSeconds())}function c(a,b){return(a.getFullYear()%1e4+1e4).toString().substr(1)+"-"+b._makeTwoDigits(a.getMonth()+1)+"-"+b._makeTwoDigits(a.getDate())}var d=null;if(a)d=this._setDate(a);else switch(this.options.type){case"time":d=b(this.options.date,this);break;case"date":d=c(this.options.date,this);break;default:d=c(this.options.date,this)+"T"+b(this.options.date,this)}return d},setValue:function(a){return console.warn("setValue was deprecated. use datetimepicker('option', 'date', value) instead."),this.value(a)},getValue:function(){return console.warn("getValue() was deprecated. use datetimepicker('value') instead."),this.value()},_updateField:function(a,b){if(!a||a.length==0)return;b==0&&(b="0");var c=a.jqmData("pat"),d,e,f=this;switch(c){case"H":case"HH":case"h":case"hh":d=b,c.charAt(0)=="h"&&(d>12?d-=12:d==0&&(d=12)),d=this._makeTwoDigits(d),e=d;break;case"m":case"M":case"d":case"s":e=b;break;case"mm":case"dd":case"MM":case"ss":e=this._makeTwoDigits(b);break;case"MMM":e=this._calendar().months.namesAbbr[b-1];break;case"MMMM":e=this._calendar().months.names[b-1];break;case"yy":e=this._makeTwoDigits(b%100);break;case"yyyy":b<10?b="000"+b:b<100?b="00"+b:b<1e3&&(b="0"+b),e=b}a.text()!=e&&(a.hasClass("ui-datefield-selected")?(a.addClass("out"),this._new_value=e,a.animationComplete(function(){a.text(f._new_value),a.addClass("in").removeClass("out"),a.animationComplete(function(){a.removeClass("in").removeClass("ui-datefield-selected")})})):a.text(e))},_switchAmPm:function(a){if(this._calendar().AM!=null){var b=new Date(this.options.date),c,d=432e5;b.getHours()>11&&(d=-d),b.setTime(b.getTime()+d),this._setDate(b)}},_parsePattern:function(a){var b=/\/|\s|dd|d|MMMM|MMM|MM|M|yyyy|yy|y|hh|h|HH|H|mm|m|ss|s|tt|t|f|gg|g|\'[\w\W]*\'$|[\w\W]/g,c,d;c=a.match(b);for(d=0;d<c.length;d++)c[d].charAt(0)=="'"&&(c[d]=c[d].substr(1,c[d].length-2));return c},changeTypeFormat:function(a,b){console.warn('changeTypeFormat() was deprecated. use datetimepicker("option", "type"|"format", value) instead'),a&&this._setType(a),b&&this._setFormat(b)},_create:function(){var c=this;this.element.is("input")&&function(a){var b,c,d;b=a.element.get(0).getAttribute("type"),a.options.type=b,c=a.element.get(0).getAttribute("value"),c&&(a.options.date=new Date(c))}(this);if(!this.options.format)switch(this.options.type){case"datetime":this.options.format=this._calendar().patterns.d+"\t"+this._calendar().patterns.t;break;case"date":this.options.format=this._calendar().patterns.d;break;case"time":this.options.format=this._calendar().patterns.t}this.options.date||(this.options.date=new Date),this.element.hide(),this.ui=a('<div class="ui-datefield"></div>'),a(this.element).after(this.ui),this._popup_open=!1,this.ui.bind("vclick",function(a){return c._showDataSelector(c,this,a.target),!1}),a.extend(this,{_globalHandlers:[{src:a(b),handler:{orientationchange:a.proxy(this,"_orientationHandler")}}]}),a.each(this._globalHandlers,function(a,b){b.src.bind(b.handler)})},_orientationHandler:function(){var a=this;return a._popup_open&&(a._popup_open=!1,a.container.popupwindow("close")),!1},_populateDataSelector:function(a,c){var d,e,f,g,h=b.range,i,j,k,l;switch(a){case"hour":c=="H"||c=="HH"?(d=h(0,23),g=h(0,23),f=this.options.date.getHours()):(d=h(1,12),f=this.options.date.getHours()-1,f>=11?(f-=12,g=h(13,23),g.push(12)):(g=h(1,11),g.push(0)),f<0&&(f=11)),c.length==2&&(d=d.map(this._makeTwoDigits)),e=d.length;break;case"min":case"sec":d=h(0,59),c.length==2&&(d=d.map(this._makeTwoDigits)),g=h(0,59),f=a=="min"?this.options.date.getMinutes():this.options.date.getSeconds(),e=d.length;break;case"year":j=1900,k=2100,g=h(j,k),f=this.options.date.getFullYear()-j,d=h(j,k),e=d.length;break;case"month":switch(c.length){case 1:d=h(1,12);break;case 2:d=h(1,12).map(this._makeTwoDigits);break;case 3:d=this._calendar().months.namesAbbr.slice();break;case 4:d=this._calendar().months.names.slice()}d.length==13&&d[12]==""&&d.pop(),g=h(1,d.length),f=this.options.date.getMonth(),e=d.length;break;case"day":l=this._daysInMonth[this.options.date.getMonth()],l==28&&(l+=this._isLeapYear(this.options.date.getFullYear())),d=h(1,l),c.length==2&&(d=d.map(this._makeTwoDigits)),g=h(1,l),f=this.options.date.getDate()-1,e=l}return{values:d,data:g,numItems:e,current:f}},_showDataSelector:function(d,e,f){f=a(f);var g=f.attr("class"),h=g?g.match(/ui-datefield-([\w]*)/):c,i,j,k,l,m,n,o,p,q,r,s,t,u,v=10,w=this;if(!g)return;if(!h)return;if(this._popup_open)return;f.not(".ui-datefield-seperator").addClass("ui-datefield-selected"),i=f.jqmData("pat"),j=d._populateDataSelector.call(d,h[1],i),k=j.values,l=j.numItems,m=j.current,n=j.data;if(k){p="data-"+(a.mobile.ns?a.mobile.ns+"-":"")+'val="';for(u=0;u<k.length;u++)o+='<li><a class="ui-link" '+p+n[u]+'">'+k[u]+"</a></li>";q=a("<ul></ul>"),r=a('<div class="ui-datetimepicker-selector" data-transition="fade" data-fade="false"></div>'),r.append(q).appendTo(e),s=r.ctxpopup(),s.parents(".ui-popupwindow").addClass("ui-datetimepicker"),t=a(o),a(t[m]).addClass("current"),r.jqmData("list",t),r.circularview(),d._reflow||(d._reflow=function(){r.circularview("reflow"),r.circularview("centerTo",".current",0)},a(b).bind("resize",d._reflow)),a(b).width()/2<f.offset().left&&(v=-10),s.popupwindow("open",f.offset().left+f.width()/2+v-b.pageXOffset,f.offset().top+f.height()-b.pageYOffset),this.container=s,this._popup_open=!0,r.bind("popupafterclose",function(c){d._reflow&&(a(b).unbind("resize",d._reflow),d._reflow=null),!f.hasClass("in")&&!f.hasClass("out")&&f.removeClass("ui-datefield-selected"),r.unbind("popupafterclose"),q.unbind("vclick"),a(d).unbind("update"),s.popupwindow("destroy"),r.remove(),w._popup_open=!1}),a(d).bind("update",function(a,b){var c=new Date(this.options.date),e,f=function(){c.setDate(1),c.setDate(c.getDate()-1)};switch(h[1]){case"min":c.setMinutes(b);break;case"hour":c.setHours(b);break;case"sec":c.setSeconds(b);break;case"year":e=c.getMonth(),c.setFullYear(b),c.getMonth()!=e&&f();break;case"month":c.setMonth(b-1),c.getMonth()==b&&f();break;case"day":c.setDate(b)}d._setDate(c),s.popupwindow("close")}),q.bind("click",function(b){if(a(b.target).is("a")){q.find(".current").removeClass("current"),a(b.target).parent().addClass("current");var c=a(b.target).jqmData("val");a(d).trigger("update",c)}}),r.circularview("centerTo",".current",500),r.bind("scrollend",function(c){d._reflow||(d._reflow=function(){r.circularview("reflow")},a(b).bind("resize",d._reflow))})}return e}}),a(document).bind("pagecreate create",function(b){a(a.tizen.datetimepicker.prototype.options.initSelector,b.target).not(":jqmData(role='none'), :jqmData(role='nojs')").datetimepicker()})}(jQuery,this),function(a){a.tizen.frameworkData.pkgVersion="0.2.27"}(jQuery);
\ No newline at end of file