[ Index ]

PHP Cross Reference of Phabricator

title

Body

[close]

/webroot/rsrc/externals/javelin/lib/ -> Resource.js (source)

   1  /**
   2   * @provides javelin-resource
   3   * @requires javelin-util
   4   *           javelin-uri
   5   *           javelin-install
   6   *
   7   * @javelin
   8   */
   9  
  10  JX.install('Resource', {
  11  
  12    statics: {
  13  
  14      _loading: {},
  15      _loaded: {},
  16      _links: [],
  17      _callbacks: [],
  18  
  19      /**
  20       * Loads one or many static resources (JavaScript or CSS) and executes a
  21       * callback once these resources have finished loading.
  22       *
  23       * @param string|array  static resource or list of resources to be loaded
  24       * @param function      callback when resources have finished loading
  25       */
  26      load: function(list, callback) {
  27        var resources = {},
  28          uri, resource, path, type;
  29  
  30        list = JX.$AX(list);
  31  
  32        // In the event there are no resources to wait on, call the callback and
  33        // exit. NOTE: it's better to do this check outside this function and not
  34        // call through JX.Resource, but it's not always easy/possible to do so
  35        if (!list.length) {
  36          setTimeout(callback, 0);
  37          return;
  38        }
  39  
  40        for (var ii = 0; ii < list.length; ii++) {
  41          uri = new JX.URI(list[ii]);
  42          resource = uri.toString();
  43          path = uri.getPath();
  44          resources[resource] = true;
  45  
  46          if (JX.Resource._loaded[resource]) {
  47            setTimeout(JX.bind(JX.Resource, JX.Resource._complete, resource), 0);
  48          } else if (!JX.Resource._loading[resource]) {
  49            JX.Resource._loading[resource] = true;
  50            if (path.indexOf('.css') == path.length - 4) {
  51              JX.Resource._loadCSS(resource);
  52            } else {
  53              JX.Resource._loadJS(resource);
  54            }
  55          }
  56        }
  57  
  58        JX.Resource._callbacks.push({
  59          resources: resources,
  60          callback: callback
  61        });
  62      },
  63  
  64      _loadJS: function(uri) {
  65        var script = document.createElement('script');
  66        var load_callback = function() {
  67          JX.Resource._complete(uri);
  68        };
  69        var error_callback = function() {
  70          JX.$E('Resource: JS file download failure: ' + uri);
  71        };
  72  
  73        JX.copy(script, {
  74          type: 'text/javascript',
  75          src: uri
  76        });
  77  
  78        script.onload = load_callback;
  79        script.onerror = error_callback;
  80        script.onreadystatechange = function() {
  81          var state = this.readyState;
  82          if (state == 'complete' || state == 'loaded') {
  83            load_callback();
  84          }
  85        };
  86        document.getElementsByTagName('head')[0].appendChild(script);
  87      },
  88  
  89      _loadCSS: function(uri) {
  90        var link = JX.copy(document.createElement('link'), {
  91          type: 'text/css',
  92          rel: 'stylesheet',
  93          href: uri,
  94          'data-href': uri // don't trust href
  95        });
  96        document.getElementsByTagName('head')[0].appendChild(link);
  97  
  98        JX.Resource._links.push(link);
  99        if (!JX.Resource._timer) {
 100          JX.Resource._timer = setInterval(JX.Resource._poll, 20);
 101        }
 102      },
 103  
 104      _poll: function() {
 105        var sheets = document.styleSheets,
 106          ii = sheets.length,
 107          links = JX.Resource._links;
 108  
 109        // Cross Origin CSS loading
 110        // http://yearofmoo.com/2011/03/cross-browser-stylesheet-preloading/
 111        while (ii--) {
 112          var link = sheets[ii],
 113            owner = link.ownerNode || link.owningElement,
 114            jj = links.length;
 115          if (owner) {
 116            while (jj--) {
 117              if (owner == links[jj]) {
 118                JX.Resource._complete(links[jj]['data-href']);
 119                links.splice(jj, 1);
 120              }
 121            }
 122          }
 123        }
 124  
 125        if (!links.length) {
 126          clearInterval(JX.Resource._timer);
 127          JX.Resource._timer = null;
 128        }
 129      },
 130  
 131      _complete: function(uri) {
 132        var list = JX.Resource._callbacks,
 133          current, ii;
 134  
 135        delete JX.Resource._loading[uri];
 136        JX.Resource._loaded[uri] = true;
 137  
 138        var errors = [];
 139        for (ii = 0; ii < list.length; ii++) {
 140          current = list[ii];
 141          delete current.resources[uri];
 142          if (!JX.Resource._hasResources(current.resources)) {
 143            try {
 144              current.callback();
 145            } catch (error) {
 146              errors.push(error);
 147            }
 148            list.splice(ii--, 1);
 149          }
 150        }
 151  
 152        if (errors.length) {
 153          throw errors[0];
 154        }
 155      },
 156  
 157      _hasResources: function(resources) {
 158        for (var hasResources in resources) {
 159          return true;
 160        }
 161        return false;
 162      }
 163  
 164    },
 165  
 166    initialize: function() {
 167      var list = JX.$A(document.getElementsByTagName('link')),
 168        ii = list.length,
 169        node;
 170      while ((node = list[--ii])) {
 171        if (node.type == 'text/css' && node.href) {
 172          JX.Resource._loaded[(new JX.URI(node.href)).toString()] = true;
 173        }
 174      }
 175  
 176      list = JX.$A(document.getElementsByTagName('script'));
 177      ii = list.length;
 178      while ((node = list[--ii])) {
 179        if (node.type == 'text/javascript' && node.src) {
 180          JX.Resource._loaded[(new JX.URI(node.src)).toString()] = true;
 181        }
 182      }
 183    }
 184  
 185  });


Generated: Sun Nov 30 09:20:46 2014 Cross-referenced by PHPXref 0.7.1