Как подождать, пока другой JS загрузится, чтобы продолжить работу?
У меня проблема. Один из моих сценариев JS требует загрузки в первую очередь Facebook SDK и Twitter виджетов JS. Facebook создает объект FB
, Twitter создает объект twttr
. Оба они создают эти объекты ПОСЛЕ того, как мои script срабатывают, даже если они загружены из <head>
.
Я думаю, что решение должно периодически проверять, определены ли FB и twttr, а затем продолжить выполнение моего script. Но я не знаю, как это сделать.
Я попытался создать цикл
while (typeof FB === 'undefined' || typeof twttr === 'undefined' || typeof twttr.widgets === 'undefined') {
// run timeout for 100 ms with noop inside
}
Но это явно не работает, так как он держит тайм-ауты на высокой скорости и зависает страницы.
Пожалуйста, помогите мне, я не могу спать из-за этой проблемы.
Ответы
Ответ 1
Если сценарии загружаются в обычном режиме синхронно, просто убедитесь, что ваш <script>
include появляется после сценариев библиотеки в документе <head>
. Если, с другой стороны, эти сценарии загружают объекты асинхронно (как представляется, это так), то создайте что-то вроде этого:
function whenAvailable(name, callback) {
var interval = 10; // ms
window.setTimeout(function() {
if (window[name]) {
callback(window[name]);
} else {
window.setTimeout(arguments.callee, interval);
}
}, interval);
}
И используйте его следующим образом:
whenAvailable("twttr", function(t) {
// do something
});
Функция, указанная во втором аргументе whenAvailable
, не будет выполняться до тех пор, пока на глобальном объекте window
не будет определена twttr
. Вы можете сделать то же самое для FB
.
Важное примечание: Эти библиотеки, возможно, также предоставляют встроенный способ выполнения кода после загрузки. Вы должны искать такие крючки в своей соответствующей документации.
Ответ 2
Вы помещаете ваш script для выполнения загрузки страницы? (т.е. body onload="do_this ();"
)
Это должно сделать ваш код выполненным после загрузки всех внешних ресурсов.
Что касается использования setTimeout
setTimeout
немедленно вернется, если вы хотите, чтобы определенная переменная была определена, используйте что-то как показано ниже.
function when_external_loaded (callback) {
if (typeof FB === 'undefined' || typeof twtter === 'undefined') {
setTimeout (function () {
when_external_loaded (callback);
}, 100); // wait 100 ms
} else { callback (); }
}
...
when_external_loaded (function () {
alert (FB);
alert (twtter);
});
Ответ 3
Если скрипты Facebook загружаются асинхронно, Facebook поддерживает способ выполнения кода при загрузке библиотеки, которая должна быть намного эффективнее, чем опрос. См. Этот ответ для примера: fooobar.com/info/191780/....
Если скрипты Facebook загружаются синхронно, вам не нужно их ждать - они будут загружаться перед любыми другими сценариями после их запуска.