Событие загрузки Javascript - как узнать, загружен ли скрипт? - PullRequest
6 голосов
/ 04 января 2011

Как я могу использовать javascript, чтобы определить, был ли HTMLScriptElement уже полностью загружен?

Как определить, завершил ли динамически загруженный скрипт загрузку без , используя события изменения onload или onreadystate?

Код выглядит следующим образом:

   TOOL.loadScript = function (url, callback, reappend, deepSearch) {
      var head, curr, child, tempScript, alreadyAppended, queue, 
      alreadyHandled, script, handler, loadFunc; 

      head = document.getElementsByTagName("head")[0];
      tempScript = document.createElement("script");
      tempScript.src = url;
      alreadyAppended = false;

      queue = []; 

      if (deepSearch) {
         // search entire document
         queue.push(document.firstElementChild);
      }
      else { 
         // just search the head element
         queue.push(head); 
      }

      while (queue.length !== 0) { 
         curr = queue.shift();

         // add child nodes to queue
         child = curr.firstElementChild; 
         if (child !== null && child !== undefined) { 
            queue.push(child);
            child = child.nextElementSibling;
            while (child !== null && child !== undefined) { 
               queue.push(child);
               child = child.nextElementSibling;
            } 
         }

         if (curr.tagName !== null && curr.tagName !== undefined) {
            if (curr.tagName.toLowerCase() === "script" && curr.src === tempScript.src) {
               script = curr;
               alreadyAppended = true;
               break;
            }
         }
      }

      if (!alreadyAppended) { 
         script = document.createElement("script");
         script.type = "text/javascript"; 
         script.async = true; 
         script.src = url; 
      } 

      alreadyHandled = false; 

      handler = function (event) {
         console.log("handling event..."); 
         if (!alreadyHandled) { 
            if ((!event.readyState) || (event && (event.readyState === "loaded" || event.readyState === "complete"))) {  
               alreadyHandled = true; 
               callback.apply(script, [url]);
               if (loadFunc) { 
                  loadFunc.apply(script, arguments); 
               }
            }
         }
      }; 

      if (script.onreadystatechange === undefined) { 
         loadFunc = script.onload;
         script.onload = handler; 
      } 
      else { 
         loadFunc = script.onreadystatechange; 
         script.onreadystatechange = handler; 
      } 

Мне нужна помощь здесь. Я хочу, чтобы функция обратного вызова сработала, даже если alreadyAppeneded === true и тот же скрипт уже загружен, но только если этот скрипт полностью завершил загрузку.

      if (!alreadyAppended || (alreadyAppended && reappend)) { 
         head.appendChild(script); 
      } 
   };

НИЖНЯЯ ЛИНИЯ: Как определить, завершился ли загрузка скрипта? Пожалуйста, задавайте мне вопросы, если это необходимо.

Спасибо.

Ответы [ 3 ]

3 голосов
/ 12 августа 2011

Почему бы не добавить идентификатор в элемент скрипта? Прежде чем продолжить, проверьте, существует ли идентификатор.

function includeJs(jsFilePath) {

  if (document.getElementById(jsFilePath+"_script")) {
    return;
  }
  var js = document.createElement("script");

  js.type = "text/javascript";
  js.id = jsFilePath+"_script";
  js.src = jsFilePath;

  document.body.appendChild(js); 
}
2 голосов
/ 04 января 2011

Ленивая реализация: Создайте массив, который вы можете использовать для переноса источника всех загруженных скриптов, и, по мере их загрузки, переносите их в список. Каждый раз проверяйте, есть ли указанный src в массиве, и если это так, немедленно запускайте обратный вызов.

Что вы делаете со случаем, когда он добавляется, но не загружается, становится вопросом. Если вы хотите, чтобы обратный вызов срабатывал, но вы хотите, чтобы он срабатывал после загрузки, вы можете создать ассоциативный массив с src в качестве ключа и элементом script в качестве значения. Оттуда дважды запустите onload или onreadystatechange, обернув оригинал, примерно так:

var temponload = element.onreadystatechange || element.onload;
if (element.onreadystatechange === undefined)
    element.onload = function(e) { temponload(); temponload(); };
else
    element.onreadystatechange = function (e) { temponload(); temponload(); };

У вас есть другой код, который может понадобиться для этого, но, надеюсь, это поможет вам начать работу.

1 голос
/ 06 января 2011

Вы не можете точно сказать, когда скрипт загрузился. Вы можете поместить глобальную переменную в скрипт, который вы хотите проверить, и затем проверить его наличие.

Существует новый проект под названием LABjs (загрузка и блокировка Javascript) для динамической загрузки сценариев и, таким образом, определения момента их фактической загрузки (http://blog.getify.com/2009/11/labjs-new-hotness-for-script-loading/ <- проверить его) </p>

...