github.com/fanux/shipyard@v0.0.0-20161009071005-6515ce223235/controller/static/semantic/src/definitions/modules/sidebar.js (about)

     1  /*!
     2   * # Semantic UI - Sidebar
     3   * http://github.com/semantic-org/semantic-ui/
     4   *
     5   *
     6   * Copyright 2014 Contributors
     7   * Released under the MIT license
     8   * http://opensource.org/licenses/MIT
     9   *
    10   */
    11  
    12  ;(function ( $, window, document, undefined ) {
    13  
    14  "use strict";
    15  
    16  $.fn.sidebar = function(parameters) {
    17    var
    18      $allModules     = $(this),
    19      $window         = $(window),
    20      $document       = $(document),
    21      $html           = $('html'),
    22      $head           = $('head'),
    23  
    24      moduleSelector  = $allModules.selector || '',
    25  
    26      time            = new Date().getTime(),
    27      performance     = [],
    28  
    29      query           = arguments[0],
    30      methodInvoked   = (typeof query == 'string'),
    31      queryArguments  = [].slice.call(arguments, 1),
    32  
    33      requestAnimationFrame = window.requestAnimationFrame
    34        || window.mozRequestAnimationFrame
    35        || window.webkitRequestAnimationFrame
    36        || window.msRequestAnimationFrame
    37        || function(callback) { setTimeout(callback, 0); },
    38  
    39      returnedValue
    40    ;
    41  
    42    $allModules
    43      .each(function() {
    44        var
    45          settings        = ( $.isPlainObject(parameters) )
    46            ? $.extend(true, {}, $.fn.sidebar.settings, parameters)
    47            : $.extend({}, $.fn.sidebar.settings),
    48  
    49          selector        = settings.selector,
    50          className       = settings.className,
    51          namespace       = settings.namespace,
    52          regExp          = settings.regExp,
    53          error           = settings.error,
    54  
    55          eventNamespace  = '.' + namespace,
    56          moduleNamespace = 'module-' + namespace,
    57  
    58          $module         = $(this),
    59          $context        = $(settings.context),
    60  
    61          $sidebars       = $module.children(selector.sidebar),
    62          $fixed          = $context.children(selector.fixed),
    63          $pusher         = $context.children(selector.pusher),
    64          $style,
    65  
    66          element         = this,
    67          instance        = $module.data(moduleNamespace),
    68  
    69          elementNamespace,
    70          id,
    71          currentScroll,
    72          transitionEvent,
    73  
    74          module
    75        ;
    76  
    77        module      = {
    78  
    79          initialize: function() {
    80            module.debug('Initializing sidebar', parameters);
    81  
    82            module.create.id();
    83  
    84            transitionEvent = module.get.transitionEvent();
    85  
    86            // cache on initialize
    87            if( ( settings.useLegacy == 'auto' && module.is.legacy() ) || settings.useLegacy === true) {
    88              settings.transition = 'overlay';
    89              settings.useLegacy = true;
    90            }
    91  
    92            if(module.is.ios()) {
    93              module.set.ios();
    94            }
    95  
    96            // avoids locking rendering if initialized in onReady
    97            if(settings.delaySetup) {
    98              requestAnimationFrame(module.setup.layout);
    99            }
   100            else {
   101              module.setup.layout();
   102            }
   103  
   104            module.instantiate();
   105          },
   106  
   107          instantiate: function() {
   108            module.verbose('Storing instance of module', module);
   109            instance = module;
   110            $module
   111              .data(moduleNamespace, module)
   112            ;
   113          },
   114  
   115          create: {
   116            id: function() {
   117              id = (Math.random().toString(16) + '000000000').substr(2,8);
   118              elementNamespace = '.' + id;
   119              module.verbose('Creating unique id for element', id);
   120            }
   121          },
   122  
   123          destroy: function() {
   124            module.verbose('Destroying previous module for', $module);
   125            module.remove.direction();
   126            $module
   127              .off(eventNamespace)
   128              .removeData(moduleNamespace)
   129            ;
   130            // bound by uuid
   131            $context.off(elementNamespace);
   132            $window.off(elementNamespace);
   133            $document.off(elementNamespace);
   134          },
   135  
   136          event: {
   137            clickaway: function(event) {
   138              var
   139                clickedInPusher = ($pusher.find(event.target).length > 0 || $pusher.is(event.target)),
   140                clickedContext  = ($context.is(event.target))
   141              ;
   142              if(clickedInPusher) {
   143                module.verbose('User clicked on dimmed page');
   144                module.hide();
   145              }
   146              if(clickedContext) {
   147                module.verbose('User clicked on dimmable context (scaled out page)');
   148                module.hide();
   149              }
   150            },
   151            touch: function(event) {
   152              //event.stopPropagation();
   153            },
   154            containScroll: function(event) {
   155              if(element.scrollTop <= 0)  {
   156                element.scrollTop = 1;
   157              }
   158              if((element.scrollTop + element.offsetHeight) >= element.scrollHeight) {
   159                element.scrollTop = element.scrollHeight - element.offsetHeight - 1;
   160              }
   161            },
   162            scroll: function(event) {
   163              if( $(event.target).closest(selector.sidebar).length === 0 ) {
   164                event.preventDefault();
   165              }
   166            }
   167          },
   168  
   169          bind: {
   170            clickaway: function() {
   171              module.verbose('Adding clickaway events to context', $context);
   172              if(settings.closable) {
   173                $context
   174                  .on('click' + elementNamespace, module.event.clickaway)
   175                  .on('touchend' + elementNamespace, module.event.clickaway)
   176                ;
   177              }
   178            },
   179            scrollLock: function() {
   180              if(settings.scrollLock) {
   181                module.debug('Disabling page scroll');
   182                $window
   183                  .on('DOMMouseScroll' + elementNamespace, module.event.scroll)
   184                ;
   185              }
   186              module.verbose('Adding events to contain sidebar scroll');
   187              $document
   188                .on('touchmove' + elementNamespace, module.event.touch)
   189              ;
   190              $module
   191                .on('scroll' + eventNamespace, module.event.containScroll)
   192              ;
   193            }
   194          },
   195          unbind: {
   196            clickaway: function() {
   197              module.verbose('Removing clickaway events from context', $context);
   198              $context.off(elementNamespace);
   199            },
   200            scrollLock: function() {
   201              module.verbose('Removing scroll lock from page');
   202              $document.off(elementNamespace);
   203              $window.off(elementNamespace);
   204              $module.off('scroll' + eventNamespace);
   205            }
   206          },
   207  
   208          add: {
   209            bodyCSS: function() {
   210              var
   211                width     = $module.outerWidth(),
   212                height    = $module.outerHeight(),
   213                direction = module.get.direction(),
   214                distance  = {
   215                  left   : width,
   216                  right  : -width,
   217                  top    : height,
   218                  bottom : -height
   219                },
   220                style
   221              ;
   222              if( module.is.rtl() ){
   223                module.verbose('RTL detected, flipping widths');
   224                distance.left = -width;
   225                distance.right = width;
   226              }
   227  
   228              style  = '<style title="' + namespace + '">';
   229  
   230              if(direction === 'left' || direction === 'right') {
   231                module.debug('Adding CSS rules for animation distance', width);
   232                style  += ''
   233                  + ' .ui.visible.' + direction + '.sidebar ~ .fixed,'
   234                  + ' .ui.visible.' + direction + '.sidebar ~ .pusher {'
   235                  + '   -webkit-transform: translate3d('+ distance[direction] + 'px, 0, 0);'
   236                  + '           transform: translate3d('+ distance[direction] + 'px, 0, 0);'
   237                  + ' }'
   238                ;
   239              }
   240              else if(direction === 'top' || direction == 'bottom') {
   241                style  += ''
   242                  + ' .ui.visible.' + direction + '.sidebar ~ .fixed,'
   243                  + ' .ui.visible.' + direction + '.sidebar ~ .pusher {'
   244                  + '   -webkit-transform: translate3d(0, ' + distance[direction] + 'px, 0);'
   245                  + '           transform: translate3d(0, ' + distance[direction] + 'px, 0);'
   246                  + ' }'
   247                ;
   248              }
   249  
   250              /* IE is only browser not to create context with transforms */
   251              /* https://www.w3.org/Bugs/Public/show_bug.cgi?id=16328 */
   252              if( module.is.ie() ) {
   253                if(direction === 'left' || direction === 'right') {
   254                  module.debug('Adding CSS rules for animation distance', width);
   255                  style  += ''
   256                    + ' body.pushable > .ui.visible.' + direction + '.sidebar ~ .pusher:after {'
   257                    + '   -webkit-transform: translate3d('+ distance[direction] + 'px, 0, 0);'
   258                    + '           transform: translate3d('+ distance[direction] + 'px, 0, 0);'
   259                    + ' }'
   260                  ;
   261                }
   262                else if(direction === 'top' || direction == 'bottom') {
   263                  style  += ''
   264                    + ' body.pushable > .ui.visible.' + direction + '.sidebar ~ .pusher:after {'
   265                    + '   -webkit-transform: translate3d(0, ' + distance[direction] + 'px, 0);'
   266                    + '           transform: translate3d(0, ' + distance[direction] + 'px, 0);'
   267                    + ' }'
   268                  ;
   269                }
   270                /* opposite sides visible forces content overlay */
   271                style += ''
   272                  + ' body.pushable > .ui.visible.left.sidebar ~ .ui.visible.right.sidebar ~ .pusher:after,'
   273                  + ' body.pushable > .ui.visible.right.sidebar ~ .ui.visible.left.sidebar ~ .pusher:after {'
   274                  + '   -webkit-transform: translate3d(0px, 0, 0);'
   275                  + '           transform: translate3d(0px, 0, 0);'
   276                  + ' }'
   277                ;
   278              }
   279              style += '</style>';
   280              $head.append(style);
   281              $style = $('style[title=' + namespace + ']');
   282              module.debug('Adding sizing css to head', $style);
   283            }
   284          },
   285  
   286          refresh: function() {
   287            module.verbose('Refreshing selector cache');
   288            $context  = $(settings.context);
   289            $sidebars = $context.children(selector.sidebar);
   290            $pusher   = $context.children(selector.pusher);
   291            $fixed    = $context.children(selector.fixed);
   292          },
   293  
   294          refreshSidebars: function() {
   295            module.verbose('Refreshing other sidebars');
   296            $sidebars = $context.children(selector.sidebar);
   297          },
   298  
   299          repaint: function() {
   300            module.verbose('Forcing repaint event');
   301            element.style.display='none';
   302            element.offsetHeight;
   303            element.scrollTop = element.scrollTop;
   304            element.style.display='';
   305          },
   306  
   307          setup: {
   308            layout: function() {
   309              if( $context.children(selector.pusher).length === 0 ) {
   310                module.debug('Adding wrapper element for sidebar');
   311                module.error(error.pusher);
   312                $pusher = $('<div class="pusher" />');
   313                $context
   314                  .children()
   315                    .not(selector.omitted)
   316                    .not($sidebars)
   317                    .wrapAll($pusher)
   318                ;
   319                module.refresh();
   320              }
   321              if($module.nextAll(selector.pusher).length === 0 || $module.nextAll(selector.pusher)[0] !== $pusher[0]) {
   322                module.debug('Moved sidebar to correct parent element');
   323                module.error(error.movedSidebar, element);
   324                $module.detach().prependTo($context);
   325                module.refresh();
   326              }
   327              module.set.pushable();
   328              module.set.direction();
   329            }
   330          },
   331  
   332          attachEvents: function(selector, event) {
   333            var
   334              $toggle = $(selector)
   335            ;
   336            event = $.isFunction(module[event])
   337              ? module[event]
   338              : module.toggle
   339            ;
   340            if($toggle.length > 0) {
   341              module.debug('Attaching sidebar events to element', selector, event);
   342              $toggle
   343                .on('click' + eventNamespace, event)
   344              ;
   345            }
   346            else {
   347              module.error(error.notFound, selector);
   348            }
   349          },
   350  
   351          show: function(callback) {
   352            var
   353              animateMethod = (settings.useLegacy === true)
   354                ? module.legacyPushPage
   355                : module.pushPage
   356            ;
   357            callback = $.isFunction(callback)
   358              ? callback
   359              : function(){}
   360            ;
   361            if(module.is.hidden()) {
   362              module.refreshSidebars();
   363              if(settings.overlay)  {
   364                module.error(error.overlay);
   365                settings.transition = 'overlay';
   366              }
   367              module.refresh();
   368              if(module.othersActive()) {
   369                module.debug('Other sidebars currently visible');
   370                if(settings.exclusive) {
   371                  // if not overlay queue animation after hide
   372                  if(settings.transition != 'overlay') {
   373                    module.hideOthers(module.show);
   374                    return;
   375                  }
   376                  else {
   377                    module.hideOthers();
   378                  }
   379                }
   380                else {
   381                  settings.transition = 'overlay';
   382                }
   383              }
   384              animateMethod(function() {
   385                callback.call(element);
   386                settings.onShow.call(element);
   387              });
   388              settings.onChange.call(element);
   389              settings.onVisible.call(element);
   390            }
   391            else {
   392              module.debug('Sidebar is already visible');
   393            }
   394          },
   395  
   396          hide: function(callback) {
   397            var
   398              animateMethod = (settings.useLegacy === true)
   399                ? module.legacyPullPage
   400                : module.pullPage
   401            ;
   402            callback = $.isFunction(callback)
   403              ? callback
   404              : function(){}
   405            ;
   406            if(module.is.visible() || module.is.animating()) {
   407              module.debug('Hiding sidebar', callback);
   408              module.refreshSidebars();
   409              animateMethod(function() {
   410                callback.call(element);
   411                settings.onHidden.call(element);
   412              });
   413              settings.onChange.call(element);
   414              settings.onHide.call(element);
   415            }
   416          },
   417  
   418          othersAnimating: function() {
   419            return ($sidebars.not($module).filter('.' + className.animating).length > 0);
   420          },
   421          othersVisible: function() {
   422            return ($sidebars.not($module).filter('.' + className.visible).length > 0);
   423          },
   424          othersActive: function() {
   425            return(module.othersVisible() || module.othersAnimating());
   426          },
   427  
   428          hideOthers: function(callback) {
   429            var
   430              $otherSidebars = $sidebars.not($module).filter('.' + className.visible),
   431              sidebarCount   = $otherSidebars.length,
   432              callbackCount  = 0
   433            ;
   434            callback = callback || function(){};
   435            $otherSidebars
   436              .sidebar('hide', function() {
   437                callbackCount++;
   438                if(callbackCount == sidebarCount) {
   439                  callback();
   440                }
   441              })
   442            ;
   443          },
   444  
   445          toggle: function() {
   446            module.verbose('Determining toggled direction');
   447            if(module.is.hidden()) {
   448              module.show();
   449            }
   450            else {
   451              module.hide();
   452            }
   453          },
   454  
   455          pushPage: function(callback) {
   456            var
   457              transition = module.get.transition(),
   458              $transition = (transition == 'safe')
   459                ? $context
   460                : (transition === 'overlay' || module.othersActive())
   461                  ? $module
   462                  : $pusher,
   463              animate,
   464              transitionEnd
   465            ;
   466            callback = $.isFunction(callback)
   467              ? callback
   468              : function(){}
   469            ;
   470            if(settings.transition == 'scale down') {
   471              module.scrollToTop();
   472            }
   473            module.set.transition(transition);
   474            module.repaint();
   475            animate = function() {
   476              module.bind.clickaway();
   477              module.add.bodyCSS();
   478              module.set.animating();
   479              module.set.visible();
   480              if(!module.othersVisible()) {
   481                if(settings.dimPage) {
   482                  $pusher.addClass(className.dimmed);
   483                }
   484              }
   485            };
   486            transitionEnd = function(event) {
   487              if( event.target == $transition[0] ) {
   488                $transition.off(transitionEvent + elementNamespace, transitionEnd);
   489                module.remove.animating();
   490                module.bind.scrollLock();
   491                callback.call(element);
   492              }
   493            };
   494            $transition.off(transitionEvent + elementNamespace);
   495            $transition.on(transitionEvent + elementNamespace, transitionEnd);
   496            requestAnimationFrame(animate);
   497          },
   498  
   499          pullPage: function(callback) {
   500            var
   501              transition = module.get.transition(),
   502              $transition = (transition == 'safe')
   503                ? $context
   504                : (transition == 'overlay' || module.othersActive())
   505                  ? $module
   506                  : $pusher,
   507              animate,
   508              transitionEnd
   509            ;
   510            callback = $.isFunction(callback)
   511              ? callback
   512              : function(){}
   513            ;
   514            module.verbose('Removing context push state', module.get.direction());
   515  
   516            module.set.transition(transition);
   517            module.unbind.clickaway();
   518            module.unbind.scrollLock();
   519  
   520            animate = function() {
   521              module.set.animating();
   522              module.remove.visible();
   523              if(settings.dimPage && !module.othersVisible()) {
   524                $pusher.removeClass(className.dimmed);
   525              }
   526            };
   527            transitionEnd = function(event) {
   528              if( event.target == $transition[0] ) {
   529                $transition.off(transitionEvent + elementNamespace, transitionEnd);
   530                module.remove.animating();
   531                module.remove.transition();
   532                module.remove.bodyCSS();
   533                if(transition == 'scale down' || (settings.returnScroll && module.is.mobile()) ) {
   534                  module.scrollBack();
   535                }
   536                callback.call(element);
   537              }
   538            };
   539            $transition.off(transitionEvent + elementNamespace);
   540            $transition.on(transitionEvent + elementNamespace, transitionEnd);
   541            requestAnimationFrame(animate);
   542          },
   543  
   544          legacyPushPage: function(callback) {
   545            var
   546              distance   = $module.width(),
   547              direction  = module.get.direction(),
   548              properties = {}
   549            ;
   550            distance  = distance || $module.width();
   551            callback  = $.isFunction(callback)
   552              ? callback
   553              : function(){}
   554            ;
   555            properties[direction] = distance;
   556            module.debug('Using javascript to push context', properties);
   557            module.set.visible();
   558            module.set.transition();
   559            module.set.animating();
   560            if(settings.dimPage) {
   561              $pusher.addClass(className.dimmed);
   562            }
   563            $context
   564              .css('position', 'relative')
   565              .animate(properties, settings.duration, settings.easing, function() {
   566                module.remove.animating();
   567                module.bind.clickaway();
   568                callback.call(element);
   569              })
   570            ;
   571          },
   572          legacyPullPage: function(callback) {
   573            var
   574              distance   = 0,
   575              direction  = module.get.direction(),
   576              properties = {}
   577            ;
   578            distance  = distance || $module.width();
   579            callback  = $.isFunction(callback)
   580              ? callback
   581              : function(){}
   582            ;
   583            properties[direction] = '0px';
   584            module.debug('Using javascript to pull context', properties);
   585            module.unbind.clickaway();
   586            module.set.animating();
   587            module.remove.visible();
   588            if(settings.dimPage && !module.othersActive()) {
   589              $pusher.removeClass(className.dimmed);
   590            }
   591            $context
   592              .css('position', 'relative')
   593              .animate(properties, settings.duration, settings.easing, function() {
   594                module.remove.animating();
   595                callback.call(element);
   596              })
   597            ;
   598          },
   599  
   600          scrollToTop: function() {
   601            module.verbose('Scrolling to top of page to avoid animation issues');
   602            currentScroll = $(window).scrollTop();
   603            $module.scrollTop(0);
   604            window.scrollTo(0, 0);
   605          },
   606  
   607          scrollBack: function() {
   608            module.verbose('Scrolling back to original page position');
   609            window.scrollTo(0, currentScroll);
   610          },
   611  
   612          set: {
   613            // html
   614            ios: function() {
   615              $html.addClass(className.ios);
   616            },
   617  
   618            // container
   619            pushed: function() {
   620              $context.addClass(className.pushed);
   621            },
   622            pushable: function() {
   623              $context.addClass(className.pushable);
   624            },
   625  
   626            // sidebar
   627            active: function() {
   628              $module.addClass(className.active);
   629            },
   630            animating: function() {
   631              $module.addClass(className.animating);
   632            },
   633            transition: function(transition) {
   634              transition = transition || module.get.transition();
   635              $module.addClass(transition);
   636            },
   637            direction: function(direction) {
   638              direction = direction || module.get.direction();
   639              $module.addClass(className[direction]);
   640            },
   641            visible: function() {
   642              $module.addClass(className.visible);
   643            },
   644            overlay: function() {
   645              $module.addClass(className.overlay);
   646            }
   647          },
   648          remove: {
   649  
   650            bodyCSS: function() {
   651              module.debug('Removing body css styles', $style);
   652              if($style && $style.length > 0) {
   653                $style.remove();
   654              }
   655            },
   656  
   657            // context
   658            pushed: function() {
   659              $context.removeClass(className.pushed);
   660            },
   661            pushable: function() {
   662              $context.removeClass(className.pushable);
   663            },
   664  
   665            // sidebar
   666            active: function() {
   667              $module.removeClass(className.active);
   668            },
   669            animating: function() {
   670              $module.removeClass(className.animating);
   671            },
   672            transition: function(transition) {
   673              transition = transition || module.get.transition();
   674              $module.removeClass(transition);
   675            },
   676            direction: function(direction) {
   677              direction = direction || module.get.direction();
   678              $module.removeClass(className[direction]);
   679            },
   680            visible: function() {
   681              $module.removeClass(className.visible);
   682            },
   683            overlay: function() {
   684              $module.removeClass(className.overlay);
   685            }
   686          },
   687  
   688          get: {
   689            direction: function() {
   690              if($module.hasClass(className.top)) {
   691                return className.top;
   692              }
   693              else if($module.hasClass(className.right)) {
   694                return className.right;
   695              }
   696              else if($module.hasClass(className.bottom)) {
   697                return className.bottom;
   698              }
   699              return className.left;
   700            },
   701            transition: function() {
   702              var
   703                direction = module.get.direction(),
   704                transition
   705              ;
   706              transition = ( module.is.mobile() )
   707                ? (settings.mobileTransition == 'auto')
   708                  ? settings.defaultTransition.mobile[direction]
   709                  : settings.mobileTransition
   710                : (settings.transition == 'auto')
   711                  ? settings.defaultTransition.computer[direction]
   712                  : settings.transition
   713              ;
   714              module.verbose('Determined transition', transition);
   715              return transition;
   716            },
   717            transitionEvent: function() {
   718              var
   719                element     = document.createElement('element'),
   720                transitions = {
   721                  'transition'       :'transitionend',
   722                  'OTransition'      :'oTransitionEnd',
   723                  'MozTransition'    :'transitionend',
   724                  'WebkitTransition' :'webkitTransitionEnd'
   725                },
   726                transition
   727              ;
   728              for(transition in transitions){
   729                if( element.style[transition] !== undefined ){
   730                  return transitions[transition];
   731                }
   732              }
   733            }
   734          },
   735  
   736          is: {
   737  
   738            ie: function() {
   739              var
   740                isIE11 = (!(window.ActiveXObject) && 'ActiveXObject' in window),
   741                isIE   = ('ActiveXObject' in window)
   742              ;
   743              return (isIE11 || isIE);
   744            },
   745  
   746            legacy: function() {
   747              var
   748                element    = document.createElement('div'),
   749                transforms = {
   750                  'webkitTransform' :'-webkit-transform',
   751                  'OTransform'      :'-o-transform',
   752                  'msTransform'     :'-ms-transform',
   753                  'MozTransform'    :'-moz-transform',
   754                  'transform'       :'transform'
   755                },
   756                has3D
   757              ;
   758  
   759              // Add it to the body to get the computed style.
   760              document.body.insertBefore(element, null);
   761              for (var transform in transforms) {
   762                if (element.style[transform] !== undefined) {
   763                  element.style[transform] = "translate3d(1px,1px,1px)";
   764                  has3D = window.getComputedStyle(element).getPropertyValue(transforms[transform]);
   765                }
   766              }
   767              document.body.removeChild(element);
   768              return !(has3D !== undefined && has3D.length > 0 && has3D !== 'none');
   769            },
   770            ios: function() {
   771              var
   772                userAgent = navigator.userAgent,
   773                isIOS     = userAgent.match(regExp.ios)
   774              ;
   775              if(isIOS) {
   776                module.verbose('Browser was found to be iOS', userAgent);
   777                return true;
   778              }
   779              else {
   780                return false;
   781              }
   782            },
   783            mobile: function() {
   784              var
   785                userAgent    = navigator.userAgent,
   786                isMobile     = userAgent.match(regExp.mobile)
   787              ;
   788              if(isMobile) {
   789                module.verbose('Browser was found to be mobile', userAgent);
   790                return true;
   791              }
   792              else {
   793                module.verbose('Browser is not mobile, using regular transition', userAgent);
   794                return false;
   795              }
   796            },
   797            hidden: function() {
   798              return !module.is.visible();
   799            },
   800            visible: function() {
   801              return $module.hasClass(className.visible);
   802            },
   803            // alias
   804            open: function() {
   805              return module.is.visible();
   806            },
   807            closed: function() {
   808              return module.is.hidden();
   809            },
   810            vertical: function() {
   811              return $module.hasClass(className.top);
   812            },
   813            animating: function() {
   814              return $context.hasClass(className.animating);
   815            },
   816            rtl: function () {
   817              return $module.css('direction') == 'rtl';
   818            }
   819          },
   820  
   821          setting: function(name, value) {
   822            module.debug('Changing setting', name, value);
   823            if( $.isPlainObject(name) ) {
   824              $.extend(true, settings, name);
   825            }
   826            else if(value !== undefined) {
   827              settings[name] = value;
   828            }
   829            else {
   830              return settings[name];
   831            }
   832          },
   833          internal: function(name, value) {
   834            if( $.isPlainObject(name) ) {
   835              $.extend(true, module, name);
   836            }
   837            else if(value !== undefined) {
   838              module[name] = value;
   839            }
   840            else {
   841              return module[name];
   842            }
   843          },
   844          debug: function() {
   845            if(settings.debug) {
   846              if(settings.performance) {
   847                module.performance.log(arguments);
   848              }
   849              else {
   850                module.debug = Function.prototype.bind.call(console.info, console, settings.name + ':');
   851                module.debug.apply(console, arguments);
   852              }
   853            }
   854          },
   855          verbose: function() {
   856            if(settings.verbose && settings.debug) {
   857              if(settings.performance) {
   858                module.performance.log(arguments);
   859              }
   860              else {
   861                module.verbose = Function.prototype.bind.call(console.info, console, settings.name + ':');
   862                module.verbose.apply(console, arguments);
   863              }
   864            }
   865          },
   866          error: function() {
   867            module.error = Function.prototype.bind.call(console.error, console, settings.name + ':');
   868            module.error.apply(console, arguments);
   869          },
   870          performance: {
   871            log: function(message) {
   872              var
   873                currentTime,
   874                executionTime,
   875                previousTime
   876              ;
   877              if(settings.performance) {
   878                currentTime   = new Date().getTime();
   879                previousTime  = time || currentTime;
   880                executionTime = currentTime - previousTime;
   881                time          = currentTime;
   882                performance.push({
   883                  'Name'           : message[0],
   884                  'Arguments'      : [].slice.call(message, 1) || '',
   885                  'Element'        : element,
   886                  'Execution Time' : executionTime
   887                });
   888              }
   889              clearTimeout(module.performance.timer);
   890              module.performance.timer = setTimeout(module.performance.display, 100);
   891            },
   892            display: function() {
   893              var
   894                title = settings.name + ':',
   895                totalTime = 0
   896              ;
   897              time = false;
   898              clearTimeout(module.performance.timer);
   899              $.each(performance, function(index, data) {
   900                totalTime += data['Execution Time'];
   901              });
   902              title += ' ' + totalTime + 'ms';
   903              if(moduleSelector) {
   904                title += ' \'' + moduleSelector + '\'';
   905              }
   906              if( (console.group !== undefined || console.table !== undefined) && performance.length > 0) {
   907                console.groupCollapsed(title);
   908                if(console.table) {
   909                  console.table(performance);
   910                }
   911                else {
   912                  $.each(performance, function(index, data) {
   913                    console.log(data['Name'] + ': ' + data['Execution Time']+'ms');
   914                  });
   915                }
   916                console.groupEnd();
   917              }
   918              performance = [];
   919            }
   920          },
   921          invoke: function(query, passedArguments, context) {
   922            var
   923              object = instance,
   924              maxDepth,
   925              found,
   926              response
   927            ;
   928            passedArguments = passedArguments || queryArguments;
   929            context         = element         || context;
   930            if(typeof query == 'string' && object !== undefined) {
   931              query    = query.split(/[\. ]/);
   932              maxDepth = query.length - 1;
   933              $.each(query, function(depth, value) {
   934                var camelCaseValue = (depth != maxDepth)
   935                  ? value + query[depth + 1].charAt(0).toUpperCase() + query[depth + 1].slice(1)
   936                  : query
   937                ;
   938                if( $.isPlainObject( object[camelCaseValue] ) && (depth != maxDepth) ) {
   939                  object = object[camelCaseValue];
   940                }
   941                else if( object[camelCaseValue] !== undefined ) {
   942                  found = object[camelCaseValue];
   943                  return false;
   944                }
   945                else if( $.isPlainObject( object[value] ) && (depth != maxDepth) ) {
   946                  object = object[value];
   947                }
   948                else if( object[value] !== undefined ) {
   949                  found = object[value];
   950                  return false;
   951                }
   952                else {
   953                  module.error(error.method, query);
   954                  return false;
   955                }
   956              });
   957            }
   958            if ( $.isFunction( found ) ) {
   959              response = found.apply(context, passedArguments);
   960            }
   961            else if(found !== undefined) {
   962              response = found;
   963            }
   964            if($.isArray(returnedValue)) {
   965              returnedValue.push(response);
   966            }
   967            else if(returnedValue !== undefined) {
   968              returnedValue = [returnedValue, response];
   969            }
   970            else if(response !== undefined) {
   971              returnedValue = response;
   972            }
   973            return found;
   974          }
   975        }
   976      ;
   977  
   978      if(methodInvoked) {
   979        if(instance === undefined) {
   980          module.initialize();
   981        }
   982        module.invoke(query);
   983      }
   984      else {
   985        if(instance !== undefined) {
   986          module.invoke('destroy');
   987        }
   988        module.initialize();
   989      }
   990    });
   991  
   992    return (returnedValue !== undefined)
   993      ? returnedValue
   994      : this
   995    ;
   996  };
   997  
   998  $.fn.sidebar.settings = {
   999  
  1000    name              : 'Sidebar',
  1001    namespace         : 'sidebar',
  1002  
  1003    debug             : false,
  1004    verbose           : true,
  1005    performance       : true,
  1006  
  1007    transition        : 'auto',
  1008    mobileTransition  : 'auto',
  1009  
  1010    defaultTransition : {
  1011      computer: {
  1012        left   : 'uncover',
  1013        right  : 'uncover',
  1014        top    : 'overlay',
  1015        bottom : 'overlay'
  1016      },
  1017      mobile: {
  1018        left   : 'uncover',
  1019        right  : 'uncover',
  1020        top    : 'overlay',
  1021        bottom : 'overlay'
  1022      }
  1023    },
  1024  
  1025    context           : 'body',
  1026    exclusive         : false,
  1027    closable          : true,
  1028    dimPage           : true,
  1029    scrollLock        : false,
  1030    returnScroll      : false,
  1031    delaySetup        : false,
  1032  
  1033    useLegacy         : 'auto',
  1034    duration          : 500,
  1035    easing            : 'easeInOutQuint',
  1036  
  1037    onChange          : function(){},
  1038    onShow            : function(){},
  1039    onHide            : function(){},
  1040  
  1041    onHidden          : function(){},
  1042    onVisible         : function(){},
  1043  
  1044    className         : {
  1045      active    : 'active',
  1046      animating : 'animating',
  1047      dimmed    : 'dimmed',
  1048      ios       : 'ios',
  1049      pushable  : 'pushable',
  1050      pushed    : 'pushed',
  1051      right     : 'right',
  1052      top       : 'top',
  1053      left      : 'left',
  1054      bottom    : 'bottom',
  1055      visible   : 'visible'
  1056    },
  1057  
  1058    selector: {
  1059      fixed   : '.fixed',
  1060      omitted : 'script, link, style, .ui.modal, .ui.dimmer, .ui.nag, .ui.fixed',
  1061      pusher  : '.pusher',
  1062      sidebar : '.ui.sidebar'
  1063    },
  1064  
  1065    regExp: {
  1066      ios    : /(iPad|iPhone|iPod)/g,
  1067      mobile : /Mobile|iP(hone|od|ad)|Android|BlackBerry|IEMobile|Kindle|NetFront|Silk-Accelerated|(hpw|web)OS|Fennec|Minimo|Opera M(obi|ini)|Blazer|Dolfin|Dolphin|Skyfire|Zune/g
  1068    },
  1069  
  1070    error   : {
  1071      method       : 'The method you called is not defined.',
  1072      pusher       : 'Had to add pusher element. For optimal performance make sure body content is inside a pusher element',
  1073      movedSidebar : 'Had to move sidebar. For optimal performance make sure sidebar and pusher are direct children of your body tag',
  1074      overlay      : 'The overlay setting is no longer supported, use animation: overlay',
  1075      notFound     : 'There were no elements that matched the specified selector'
  1076    }
  1077  
  1078  };
  1079  
  1080  // Adds easing
  1081  $.extend( $.easing, {
  1082    easeInOutQuint: function (x, t, b, c, d) {
  1083      if ((t/=d/2) < 1) return c/2*t*t*t*t*t + b;
  1084      return c/2*((t-=2)*t*t*t*t + 2) + b;
  1085    }
  1086  });
  1087  
  1088  
  1089  })( jQuery, window , document );