github.com/fanux/shipyard@v0.0.0-20161009071005-6515ce223235/controller/static/semantic/dist/components/progress.js (about)

     1  /*!
     2   * # Semantic UI x.x - Progress
     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.progress = function(parameters) {
    17    var
    18      $allModules    = $(this),
    19  
    20      moduleSelector = $allModules.selector || '',
    21  
    22      time           = new Date().getTime(),
    23      performance    = [],
    24  
    25      query          = arguments[0],
    26      methodInvoked  = (typeof query == 'string'),
    27      queryArguments = [].slice.call(arguments, 1),
    28  
    29      returnedValue
    30    ;
    31  
    32    $allModules
    33      .each(function() {
    34        var
    35          settings          = ( $.isPlainObject(parameters) )
    36            ? $.extend(true, {}, $.fn.progress.settings, parameters)
    37            : $.extend({}, $.fn.progress.settings),
    38  
    39          className       = settings.className,
    40          metadata        = settings.metadata,
    41          namespace       = settings.namespace,
    42          selector        = settings.selector,
    43          error           = settings.error,
    44  
    45          eventNamespace  = '.' + namespace,
    46          moduleNamespace = 'module-' + namespace,
    47  
    48          $module         = $(this),
    49          $bar            = $(this).find(selector.bar),
    50          $progress       = $(this).find(selector.progress),
    51          $label          = $(this).find(selector.label),
    52  
    53          element         = this,
    54          instance        = $module.data(moduleNamespace),
    55  
    56          animating = false,
    57          transitionEnd,
    58          module
    59        ;
    60  
    61        module = {
    62  
    63          initialize: function() {
    64            module.debug('Initializing progress bar', settings);
    65  
    66            transitionEnd = module.get.transitionEnd();
    67  
    68            module.read.metadata();
    69            module.set.duration();
    70            module.set.initials();
    71            module.instantiate();
    72          },
    73  
    74          instantiate: function() {
    75            module.verbose('Storing instance of progress', module);
    76            instance = module;
    77            $module
    78              .data(moduleNamespace, module)
    79            ;
    80          },
    81          destroy: function() {
    82            module.verbose('Destroying previous progress for', $module);
    83            clearInterval(instance.interval);
    84            module.remove.state();
    85            $module.removeData(moduleNamespace);
    86            instance = undefined;
    87          },
    88  
    89          reset: function() {
    90            module.set.percent(0);
    91          },
    92  
    93          complete: function() {
    94            if(module.percent === undefined || module.percent < 100) {
    95              module.set.percent(100);
    96            }
    97          },
    98  
    99          read: {
   100            metadata: function() {
   101              if( $module.data(metadata.percent) ) {
   102                module.verbose('Current percent value set from metadata');
   103                module.percent = $module.data(metadata.percent);
   104              }
   105              if( $module.data(metadata.total) ) {
   106                module.verbose('Total value set from metadata');
   107                module.total = $module.data(metadata.total);
   108              }
   109              if( $module.data(metadata.value) ) {
   110                module.verbose('Current value set from metadata');
   111                module.value = $module.data(metadata.value);
   112              }
   113            },
   114            currentValue: function() {
   115              return (module.value !== undefined)
   116                ? module.value
   117                : false
   118              ;
   119            }
   120          },
   121  
   122          increment: function(incrementValue) {
   123            var
   124              total          = module.total || false,
   125              edgeValue,
   126              startValue,
   127              newValue
   128            ;
   129            if(total) {
   130              startValue     = module.value || 0;
   131              incrementValue = incrementValue || 1;
   132              newValue       = startValue + incrementValue;
   133              edgeValue      = module.total;
   134              module.debug('Incrementing value by', incrementValue, startValue, edgeValue);
   135              if(newValue > edgeValue ) {
   136                module.debug('Value cannot increment above total', edgeValue);
   137                newValue = edgeValue;
   138              }
   139              module.set.progress(newValue);
   140            }
   141            else {
   142              startValue     = module.percent || 0;
   143              incrementValue = incrementValue || module.get.randomValue();
   144              newValue       = startValue + incrementValue;
   145              edgeValue      = 100;
   146              module.debug('Incrementing percentage by', incrementValue, startValue);
   147              if(newValue > edgeValue ) {
   148                module.debug('Value cannot increment above 100 percent');
   149                newValue = edgeValue;
   150              }
   151              module.set.progress(newValue);
   152            }
   153          },
   154          decrement: function(decrementValue) {
   155            var
   156              total     = module.total || false,
   157              edgeValue = 0,
   158              startValue,
   159              newValue
   160            ;
   161            if(total) {
   162              startValue     =  module.value   || 0;
   163              decrementValue =  decrementValue || 1;
   164              newValue       =  startValue - decrementValue;
   165              module.debug('Decrementing value by', decrementValue, startValue);
   166            }
   167            else {
   168              startValue     =  module.percent || 0;
   169              decrementValue =  decrementValue || module.get.randomValue();
   170              newValue       =  startValue - decrementValue;
   171              module.debug('Decrementing percentage by', decrementValue, startValue);
   172            }
   173  
   174            if(newValue < edgeValue) {
   175              module.debug('Value cannot decrement below 0');
   176              newValue = 0;
   177            }
   178            module.set.progress(newValue);
   179          },
   180  
   181          get: {
   182            text: function(templateText) {
   183              var
   184                value   = module.value                || 0,
   185                total   = module.total                || 0,
   186                percent = (module.is.visible() && animating)
   187                  ? module.get.displayPercent()
   188                  : module.percent || 0,
   189                left = (module.total > 0)
   190                  ? (total - value)
   191                  : (100 - percent)
   192              ;
   193              templateText = templateText || '';
   194              templateText = templateText
   195                .replace('{value}', value)
   196                .replace('{total}', total)
   197                .replace('{left}', left)
   198                .replace('{percent}', percent)
   199              ;
   200              module.debug('Adding variables to progress bar text', templateText);
   201              return templateText;
   202            },
   203            randomValue: function() {
   204              module.debug('Generating random increment percentage');
   205              return Math.floor((Math.random() * settings.random.max) + settings.random.min);
   206            },
   207  
   208            transitionEnd: function() {
   209              var
   210                element     = document.createElement('element'),
   211                transitions = {
   212                  'transition'       :'transitionend',
   213                  'OTransition'      :'oTransitionEnd',
   214                  'MozTransition'    :'transitionend',
   215                  'WebkitTransition' :'webkitTransitionEnd'
   216                },
   217                transition
   218              ;
   219              for(transition in transitions){
   220                if( element.style[transition] !== undefined ){
   221                  return transitions[transition];
   222                }
   223              }
   224            },
   225  
   226            // gets current displayed percentage (if animating values this is the intermediary value)
   227            displayPercent: function() {
   228              var
   229                barWidth       = $bar.width(),
   230                totalWidth     = $module.width(),
   231                minDisplay     = parseInt($bar.css('min-width'), 10),
   232                displayPercent = (barWidth > minDisplay)
   233                  ? (barWidth / totalWidth * 100)
   234                  : module.percent
   235              ;
   236              if(settings.precision === 0) {
   237                return Math.round(displayPercent);
   238              }
   239              return Math.round(displayPercent * (10 * settings.precision) / (10 * settings.precision) );
   240            },
   241  
   242            percent: function() {
   243              return module.percent || 0;
   244            },
   245            value: function() {
   246              return module.value || false;
   247            },
   248            total: function() {
   249              return module.total || false;
   250            }
   251          },
   252  
   253          is: {
   254            success: function() {
   255              return $module.hasClass(className.success);
   256            },
   257            warning: function() {
   258              return $module.hasClass(className.warning);
   259            },
   260            error: function() {
   261              return $module.hasClass(className.error);
   262            },
   263            active: function() {
   264              return $module.hasClass(className.active);
   265            },
   266            visible: function() {
   267              return $module.is(':visible');
   268            }
   269          },
   270  
   271          remove: {
   272            state: function() {
   273              module.verbose('Removing stored state');
   274              delete module.total;
   275              delete module.percent;
   276              delete module.value;
   277            },
   278            active: function() {
   279              module.verbose('Removing active state');
   280              $module.removeClass(className.active);
   281            },
   282            success: function() {
   283              module.verbose('Removing success state');
   284              $module.removeClass(className.success);
   285            },
   286            warning: function() {
   287              module.verbose('Removing warning state');
   288              $module.removeClass(className.warning);
   289            },
   290            error: function() {
   291              module.verbose('Removing error state');
   292              $module.removeClass(className.error);
   293            }
   294          },
   295  
   296          set: {
   297            barWidth: function(value) {
   298              if(value > 100) {
   299                module.error(error.tooHigh, value);
   300              }
   301              else if (value < 0) {
   302                module.error(error.tooLow, value);
   303              }
   304              else {
   305                $bar
   306                  .css('width', value + '%')
   307                ;
   308                $module
   309                  .attr('data-percent', parseInt(value, 10))
   310                ;
   311              }
   312            },
   313            duration: function(duration) {
   314              duration = duration || settings.duration;
   315              duration = (typeof duration == 'number')
   316                ? duration + 'ms'
   317                : duration
   318              ;
   319              module.verbose('Setting progress bar transition duration', duration);
   320              $bar
   321                .css({
   322                  '-webkit-transition-duration': duration,
   323                  '-moz-transition-duration': duration,
   324                  '-ms-transition-duration': duration,
   325                  '-o-transition-duration': duration,
   326                  'transition-duration':  duration
   327                })
   328              ;
   329            },
   330            initials: function() {
   331              if(settings.total !== false) {
   332                module.verbose('Current total set in settings', settings.total);
   333                module.total = settings.total;
   334              }
   335              if(settings.value !== false) {
   336                module.verbose('Current value set in settings', settings.value);
   337                module.value = settings.value;
   338              }
   339              if(settings.percent !== false) {
   340                module.verbose('Current percent set in settings', settings.percent);
   341                module.percent = settings.percent;
   342              }
   343              if(module.percent !== undefined) {
   344                module.set.percent(module.percent);
   345              }
   346              else if(module.value !== undefined) {
   347                module.set.progress(module.value);
   348              }
   349            },
   350            percent: function(percent) {
   351              percent = (typeof percent == 'string')
   352                ? +(percent.replace('%', ''))
   353                : percent
   354              ;
   355              if(percent > 0 && percent < 1) {
   356                module.verbose('Module percentage passed as decimal, converting');
   357                percent = percent * 100;
   358              }
   359              // round percentage
   360              if(settings.precision === 0) {
   361                percent = Math.round(percent);
   362              }
   363              else {
   364                percent = Math.round(percent * (10 * settings.precision) / (10 * settings.precision) );
   365              }
   366              module.percent = percent;
   367              if(module.total) {
   368                module.value = Math.round( (percent / 100) * module.total);
   369              }
   370              else if(settings.limitValues) {
   371                module.value = (module.value > 100)
   372                  ? 100
   373                  : (module.value < 0)
   374                    ? 0
   375                    : module.value
   376                ;
   377              }
   378              module.set.barWidth(percent);
   379              if( module.is.visible() ) {
   380                module.set.labelInterval();
   381              }
   382              module.set.labels();
   383              settings.onChange.call(element, percent, module.value, module.total);
   384            },
   385            labelInterval: function() {
   386              var
   387                animationCallback = function() {
   388                  module.verbose('Bar finished animating, removing continuous label updates');
   389                  clearInterval(module.interval);
   390                  animating = false;
   391                  module.set.labels();
   392                }
   393              ;
   394              clearInterval(module.interval);
   395              $bar.one(transitionEnd + eventNamespace, animationCallback);
   396              module.timer = setTimeout(animationCallback, settings.duration + 100);
   397              animating = true;
   398              module.interval = setInterval(module.set.labels, settings.framerate);
   399            },
   400            labels: function() {
   401              module.verbose('Setting both bar progress and outer label text');
   402              module.set.barLabel();
   403              module.set.state();
   404            },
   405            label: function(text) {
   406              text = text || '';
   407              if(text) {
   408                text = module.get.text(text);
   409                module.debug('Setting label to text', text);
   410                $label.text(text);
   411              }
   412            },
   413            state: function(percent) {
   414              percent = (percent !== undefined)
   415                ? percent
   416                : module.percent
   417              ;
   418              if(percent === 100) {
   419                if(settings.autoSuccess && !(module.is.warning() || module.is.error())) {
   420                  module.set.success();
   421                  module.debug('Automatically triggering success at 100%');
   422                }
   423                else {
   424                  module.verbose('Reached 100% removing active state');
   425                  module.remove.active();
   426                }
   427              }
   428              else if(percent > 0) {
   429                module.verbose('Adjusting active progress bar label', percent);
   430                module.set.active();
   431              }
   432              else {
   433                module.remove.active();
   434                module.set.label(settings.text.active);
   435              }
   436            },
   437            barLabel: function(text) {
   438              if(text !== undefined) {
   439                $progress.text( module.get.text(text) );
   440              }
   441              else if(settings.label == 'ratio' && module.total) {
   442                module.debug('Adding ratio to bar label');
   443                $progress.text( module.get.text(settings.text.ratio) );
   444              }
   445              else if(settings.label == 'percent') {
   446                module.debug('Adding percentage to bar label');
   447                $progress.text( module.get.text(settings.text.percent) );
   448              }
   449            },
   450            active: function(text) {
   451              text = text || settings.text.active;
   452              module.debug('Setting active state');
   453              if(settings.showActivity && !module.is.active() ) {
   454                $module.addClass(className.active);
   455              }
   456              module.remove.warning();
   457              module.remove.error();
   458              module.remove.success();
   459              if(text) {
   460                module.set.label(text);
   461              }
   462              settings.onActive.call(element, module.value, module.total);
   463            },
   464            success : function(text) {
   465              text = text || settings.text.success;
   466              module.debug('Setting success state');
   467              $module.addClass(className.success);
   468              module.remove.active();
   469              module.remove.warning();
   470              module.remove.error();
   471              module.complete();
   472              if(text) {
   473                module.set.label(text);
   474              }
   475              settings.onSuccess.call(element, module.total);
   476            },
   477            warning : function(text) {
   478              text = text || settings.text.warning;
   479              module.debug('Setting warning state');
   480              $module.addClass(className.warning);
   481              module.remove.active();
   482              module.remove.success();
   483              module.remove.error();
   484              module.complete();
   485              if(text) {
   486                module.set.label(text);
   487              }
   488              settings.onWarning.call(element, module.value, module.total);
   489            },
   490            error : function(text) {
   491              text = text || settings.text.error;
   492              module.debug('Setting error state');
   493              $module.addClass(className.error);
   494              module.remove.active();
   495              module.remove.success();
   496              module.remove.warning();
   497              module.complete();
   498              if(text) {
   499                module.set.label(text);
   500              }
   501              settings.onError.call(element, module.value, module.total);
   502            },
   503            total: function(totalValue) {
   504              module.total = totalValue;
   505            },
   506            progress: function(value) {
   507              var
   508                numericValue = (typeof value === 'string')
   509                  ? (value.replace(/[^\d.]/g, '') !== '')
   510                    ? +(value.replace(/[^\d.]/g, ''))
   511                    : false
   512                  : value,
   513                percentComplete
   514              ;
   515              if(numericValue === false) {
   516                module.error(error.nonNumeric, value);
   517              }
   518              if(module.total) {
   519                module.value    = numericValue;
   520                percentComplete = (numericValue / module.total) * 100;
   521                module.debug('Calculating percent complete from total', percentComplete);
   522                module.set.percent( percentComplete );
   523              }
   524              else {
   525                percentComplete = numericValue;
   526                module.debug('Setting value to exact percentage value', percentComplete);
   527                module.set.percent( percentComplete );
   528              }
   529            }
   530          },
   531  
   532          setting: function(name, value) {
   533            module.debug('Changing setting', name, value);
   534            if( $.isPlainObject(name) ) {
   535              $.extend(true, settings, name);
   536            }
   537            else if(value !== undefined) {
   538              settings[name] = value;
   539            }
   540            else {
   541              return settings[name];
   542            }
   543          },
   544          internal: function(name, value) {
   545            if( $.isPlainObject(name) ) {
   546              $.extend(true, module, name);
   547            }
   548            else if(value !== undefined) {
   549              module[name] = value;
   550            }
   551            else {
   552              return module[name];
   553            }
   554          },
   555          debug: function() {
   556            if(settings.debug) {
   557              if(settings.performance) {
   558                module.performance.log(arguments);
   559              }
   560              else {
   561                module.debug = Function.prototype.bind.call(console.info, console, settings.name + ':');
   562                module.debug.apply(console, arguments);
   563              }
   564            }
   565          },
   566          verbose: function() {
   567            if(settings.verbose && settings.debug) {
   568              if(settings.performance) {
   569                module.performance.log(arguments);
   570              }
   571              else {
   572                module.verbose = Function.prototype.bind.call(console.info, console, settings.name + ':');
   573                module.verbose.apply(console, arguments);
   574              }
   575            }
   576          },
   577          error: function() {
   578            module.error = Function.prototype.bind.call(console.error, console, settings.name + ':');
   579            module.error.apply(console, arguments);
   580          },
   581          performance: {
   582            log: function(message) {
   583              var
   584                currentTime,
   585                executionTime,
   586                previousTime
   587              ;
   588              if(settings.performance) {
   589                currentTime   = new Date().getTime();
   590                previousTime  = time || currentTime;
   591                executionTime = currentTime - previousTime;
   592                time          = currentTime;
   593                performance.push({
   594                  'Name'           : message[0],
   595                  'Arguments'      : [].slice.call(message, 1) || '',
   596                  'Element'        : element,
   597                  'Execution Time' : executionTime
   598                });
   599              }
   600              clearTimeout(module.performance.timer);
   601              module.performance.timer = setTimeout(module.performance.display, 100);
   602            },
   603            display: function() {
   604              var
   605                title = settings.name + ':',
   606                totalTime = 0
   607              ;
   608              time = false;
   609              clearTimeout(module.performance.timer);
   610              $.each(performance, function(index, data) {
   611                totalTime += data['Execution Time'];
   612              });
   613              title += ' ' + totalTime + 'ms';
   614              if(moduleSelector) {
   615                title += ' \'' + moduleSelector + '\'';
   616              }
   617              if( (console.group !== undefined || console.table !== undefined) && performance.length > 0) {
   618                console.groupCollapsed(title);
   619                if(console.table) {
   620                  console.table(performance);
   621                }
   622                else {
   623                  $.each(performance, function(index, data) {
   624                    console.log(data['Name'] + ': ' + data['Execution Time']+'ms');
   625                  });
   626                }
   627                console.groupEnd();
   628              }
   629              performance = [];
   630            }
   631          },
   632          invoke: function(query, passedArguments, context) {
   633            var
   634              object = instance,
   635              maxDepth,
   636              found,
   637              response
   638            ;
   639            passedArguments = passedArguments || queryArguments;
   640            context         = element         || context;
   641            if(typeof query == 'string' && object !== undefined) {
   642              query    = query.split(/[\. ]/);
   643              maxDepth = query.length - 1;
   644              $.each(query, function(depth, value) {
   645                var camelCaseValue = (depth != maxDepth)
   646                  ? value + query[depth + 1].charAt(0).toUpperCase() + query[depth + 1].slice(1)
   647                  : query
   648                ;
   649                if( $.isPlainObject( object[camelCaseValue] ) && (depth != maxDepth) ) {
   650                  object = object[camelCaseValue];
   651                }
   652                else if( object[camelCaseValue] !== undefined ) {
   653                  found = object[camelCaseValue];
   654                  return false;
   655                }
   656                else if( $.isPlainObject( object[value] ) && (depth != maxDepth) ) {
   657                  object = object[value];
   658                }
   659                else if( object[value] !== undefined ) {
   660                  found = object[value];
   661                  return false;
   662                }
   663                else {
   664                  module.error(error.method, query);
   665                  return false;
   666                }
   667              });
   668            }
   669            if ( $.isFunction( found ) ) {
   670              response = found.apply(context, passedArguments);
   671            }
   672            else if(found !== undefined) {
   673              response = found;
   674            }
   675            if($.isArray(returnedValue)) {
   676              returnedValue.push(response);
   677            }
   678            else if(returnedValue !== undefined) {
   679              returnedValue = [returnedValue, response];
   680            }
   681            else if(response !== undefined) {
   682              returnedValue = response;
   683            }
   684            return found;
   685          }
   686        };
   687  
   688        if(methodInvoked) {
   689          if(instance === undefined) {
   690            module.initialize();
   691          }
   692          module.invoke(query);
   693        }
   694        else {
   695          if(instance !== undefined) {
   696            instance.invoke('destroy');
   697          }
   698          module.initialize();
   699        }
   700      })
   701    ;
   702  
   703    return (returnedValue !== undefined)
   704      ? returnedValue
   705      : this
   706    ;
   707  };
   708  
   709  $.fn.progress.settings = {
   710  
   711    name         : 'Progress',
   712    namespace    : 'progress',
   713  
   714    debug        : false,
   715    verbose      : true,
   716    performance  : true,
   717  
   718    random       : {
   719      min : 2,
   720      max : 5
   721    },
   722  
   723    duration     : 300,
   724  
   725    autoSuccess  : true,
   726    showActivity : true,
   727    limitValues  : true,
   728  
   729    label        : 'percent',
   730    precision    : 1,
   731    framerate    : (1000 / 30), /// 30 fps
   732  
   733    percent      : false,
   734    total        : false,
   735    value        : false,
   736  
   737    onChange     : function(percent, value, total){},
   738    onSuccess    : function(total){},
   739    onActive     : function(value, total){},
   740    onError      : function(value, total){},
   741    onWarning    : function(value, total){},
   742  
   743    error    : {
   744      method     : 'The method you called is not defined.',
   745      nonNumeric : 'Progress value is non numeric',
   746      tooHigh    : 'Value specified is above 100%',
   747      tooLow     : 'Value specified is below 0%'
   748    },
   749  
   750    regExp: {
   751      variable: /\{\$*[A-z0-9]+\}/g
   752    },
   753  
   754    metadata: {
   755      percent : 'percent',
   756      total   : 'total',
   757      value   : 'value'
   758    },
   759  
   760    selector : {
   761      bar      : '> .bar',
   762      label    : '> .label',
   763      progress : '.bar > .progress'
   764    },
   765  
   766    text : {
   767      active  : false,
   768      error   : false,
   769      success : false,
   770      warning : false,
   771      percent : '{percent}%',
   772      ratio   : '{value} of {total}'
   773    },
   774  
   775    className : {
   776      active  : 'active',
   777      error   : 'error',
   778      success : 'success',
   779      warning : 'warning'
   780    }
   781  
   782  };
   783  
   784  
   785  })( jQuery, window , document );