Принудительное обновление DOM в Internet Explorer после манипуляций с javascript dom
Здесь ситуация. У меня есть некоторые JavaScript, который выглядит так:
function onSubmit() {
doSomeStuff();
someSpan.style.display="block";
otherSpan.style.display="none";
return doLongRunningOperation;
}
Когда я делаю это действие отправки формы и запускаю его из браузера, отличного от IE, он быстро меняет видимость двух диапазонов и запускает длинную операцию JavaScript. Если я делаю это в IE, он не выполняет своп до тех пор, пока onSubmit() полностью не вернется.
Я могу принудительно перерисовать дом, вставив окно предупреждения следующим образом:
function onSubmit() {
doSomeStuff();
someSpan.style.display="block";
otherSpan.style.display="none";
alert("refresh forced");
return doLongRunningOperation;
}
Кроме того, очевидный рефакторинг jquery не влияет на поведение IE:
function onSubmit() {
doSomeStuff();
$("#someSpan").show();
$("#otherSpan").hide();
return doLongRunningOperation;
}
Такое поведение существует в IE8 и IE6. Есть ли способ принудительно перерисовать DOM в этих браузерах?
6 ответов
Mozilla (возможно, также IE) будет кэшировать / задерживать выполнение изменений в DOM, которые влияют на отображение, так что он может рассчитывать все изменения сразу, а не многократно после каждого оператора.
Для принудительного обновления (для принудительного немедленного, синхронного перекомпоновки или ретрансляции) ваш javascript должен прочитать свойство, на которое повлияло изменение, например расположение someSpan и otherSpan.
(Эта деталь реализации Mozilla упоминается в видео " Быстрее HTML и CSS: Внутренние компоненты движка Layout для веб-разработчиков".)
Чтобы продолжить то, что говорит ChrisW:
вот сценарий очистки для прошивки DOM, поэтому вам не нужно вызывать alert(""); (находится по адресу http://amolnw.wordpress.com/category/programming/javascript/):
function flushThis(id){
var msie = 'Microsoft Internet Explorer';
var tmp = 0;
var elementOnShow = document.getElementById(id);
if (navigator.appName == msie){
tmp = elementOnShow.parentNode.offsetTop + 'px';
}else{
tmp = elementOnShow.offsetTop;
}
}
Меня устраивает!!! Спасибо за чаевые.
У меня была эта проблема в Chrome 21 при перетаскивании слова с буквой по убыванию ('g'). Он оставлял на экране след от мотылька, который исчезал в следующий раз, когда что-то заставляло экран обновляться. Решение ChrisW (опрос свойства, чувствительного к макету) не сработало.
Что сработало, так это добавление пустого div в 1 пиксель вверху страницы, а затем удаление его через миллисекунду, вызвав следующую функцию в конце операции перетаскивания:
// Needed by Chrome, as of Release 21. Triggers a screen refresh, removing drag garbage.
function cleanDisplay() {
var c = document.createElement('div');
c.innerHTML = 'x';
c.style.visibility = 'hidden';
c.style.height = '1px';
document.body.insertBefore(c, document.body.firstChild);
window.setTimeout(function() {document.body.removeChild(c)}, 1);
}
Примечание: вам нужна задержка. Просто добавляя и удаляя div
не работает Так же div
должен быть добавлен над той частью страницы, которая должна быть перерисована.
Вы также можете обернуть свою долгосрочную функцию в setTimeout(function(){longTerm();},1);
element.focus() у меня работает в IE10
function displayOnOff(){
var elm = document.getElementById("myDiv");
elm.style.display="block";
elm.focus();
for(var i=0; i<1000000; i++){
console.log("waiting...............");
}
elm.style.display = "none";
}