arnaucube
arnaucube/commonroutesAppPublic Self-hosted repository
commonroutesApp/www/lib/angular-material/angular-material-mocks.js
www/lib/angular-material/angular-material-mocks.jsRaw
  1/**
  2 *
  3 * Angular-Material-Mocks
  4 *
  5 * Developers interested in running their own custom unit tests WITH angular-material.js loaded...
  6 * must also include this *mocks* file. Similar to `angular-mocks.js`, `angular-material-mocks.js`
  7 * will override and disable specific Angular Material performance settings:
  8 *
  9 *  - Disabled Theme CSS rule generations
 10 *  - Forces $mdAria.expectWithText() to be synchronous
 11 *  - Mocks $$rAF.throttle()
 12 *  - Captures flush exceptions from $$rAF
 13 *
 14 */
 15(function(window, angular, undefined) {
 16
 17'use strict';
 18
 19/**
 20 * @ngdoc module
 21 * @name ngMaterial-mock
 22 * @packageName angular-material-mocks
 23 *
 24 * @description
 25 *
 26 * The `ngMaterial-mock` module provides support
 27 *
 28 */
 29angular.module('ngMaterial-mock', [
 30  'ngMock',
 31  'ngAnimateMock',
 32  'material.core'
 33  ])
 34  .config(['$provide', function($provide) {
 35
 36    $provide.factory('$material', ['$animate', '$timeout', function($animate, $timeout) {
 37      return {
 38        flushOutstandingAnimations: function() {
 39          // this code is placed in a try-catch statement
 40          // since 1.3 and 1.4 handle their animations differently
 41          // and there may be situations where follow-up animations
 42          // are run in one version and not the other
 43          try { $animate.flush(); } catch(e) {}
 44        },
 45        flushInterimElement: function() {
 46          this.flushOutstandingAnimations();
 47          $timeout.flush();
 48          this.flushOutstandingAnimations();
 49          $timeout.flush();
 50          this.flushOutstandingAnimations();
 51          $timeout.flush();
 52        }
 53      };
 54    }]);
 55
 56    /**
 57      * Angular Material dynamically generates Style tags
 58      * based on themes and palletes; for each ng-app.
 59      *
 60      * For testing, we want to disable generation and
 61      * <style> DOM injections. So we clear the huge THEME
 62      * styles while testing...
 63      */
 64     $provide.constant('$MD_THEME_CSS', '/**/');
 65
 66    /**
 67     * Add throttle() and wrap .flush() to catch `no callbacks present`
 68     * errors
 69     */
 70    $provide.decorator('$$rAF', function throttleInjector($delegate){
 71
 72      $delegate.throttle = function(cb) {
 73        return function() {
 74          cb.apply(this, arguments);
 75        };
 76      };
 77
 78      var ngFlush = $delegate.flush;
 79      $delegate.flush = function() {
 80        try      { ngFlush();  }
 81        catch(e) { ;           }
 82      };
 83
 84      return $delegate;
 85    });
 86
 87    /**
 88     * Capture $timeout.flush() errors: "No deferred tasks to be flushed"
 89     * errors
 90     */
 91    $provide.decorator('$timeout', function throttleInjector($delegate){
 92
 93      var ngFlush = $delegate.flush;
 94      $delegate.flush = function() {
 95          var args = Array.prototype.slice.call(arguments);
 96          try      { ngFlush.apply($delegate, args);  }
 97          catch(e) { }
 98      };
 99
100      return $delegate;
101    });
102
103  }]);
104
105  /**
106   * Stylesheet Mocks used by `animateCss.spec.js`
107   */
108  window.createMockStyleSheet = function createMockStyleSheet(doc, wind) {
109    doc = doc ? doc[0] : window.document;
110    wind = wind || window;
111
112    var node = doc.createElement('style');
113    var head = doc.getElementsByTagName('head')[0];
114    head.appendChild(node);
115
116    var ss = doc.styleSheets[doc.styleSheets.length - 1];
117
118    return {
119      addRule: function(selector, styles) {
120        styles = addVendorPrefix(styles);
121
122        try {
123          ss.insertRule(selector + '{ ' + styles + '}', 0);
124        }
125        catch (e) {
126          try {
127            ss.addRule(selector, styles);
128          }
129          catch (e2) {}
130        }
131      },
132
133      destroy: function() {
134        head.removeChild(node);
135      }
136    };
137
138    /**
139     * Decompose styles, attached specific vendor prefixes
140     * and recompose...
141     * e.g.
142     *    'transition:0.5s linear all; font-size:100px;'
143     * becomes
144     *    '-webkit-transition:0.5s linear all; transition:0.5s linear all; font-size:100px;'
145     */
146    function addVendorPrefix(styles) {
147      var cache = { };
148
149      // Decompose into cache registry
150      styles
151        .match(/([\-A-Za-z]*)\w\:\w*([A-Za-z0-9\.\-\s]*)/gi)
152        .forEach(function(style){
153          var pair = style.split(":");
154          var key = pair[0];
155
156          switch(key) {
157            case 'transition':
158            case 'transform':
159            case 'animation':
160            case 'transition-duration':
161            case 'animation-duration':
162              cache[key] = cache['-webkit-' + key] = pair[1];
163              break;
164            default:
165              cache[key] = pair[1];
166          }
167        });
168
169        // Recompose full style object (as string)
170        styles = "";
171        angular.forEach(cache, function(value, key) {
172          styles = styles + key + ":" + value + "; ";
173        });
174
175        return styles;
176    }
177
178  };
179
180})(window, window.angular);