Я разработал несколько улучшенных страниц с javascript, которые отлично работают в последних версиях Firefox и Safari. Я пропустил проверку в Internet Explorer, и теперь обнаружил, что страницы не работают в IE 6 и 7 (пока). Скрипты почему-то не выполняются, страницы выглядят так, как будто javascript не было, хотя какой-то javascript выполняется. Я использую собственные библиотеки с манипуляциями с dom, из YUI 2 я использую YUI-Loader и XML-Http-Request, а на одной странице я использую «psupload», который зависит от JQuery.
Я устанавливаю Microsoft Script Editor из Office XP и теперь буду выполнять отладку. Я тоже сейчас напишу конкретные тесты.
Каковы типичные недостатки IE? В каком направлении я могу держать глаза открытыми.
Я нашел эту страницу, на которой видны некоторые различия. посетите: Quirksmode
Можете ли вы по своему опыту назвать некоторые типичные вещи, которые мне следует искать в первую очередь?
Позже я также задам дополнительные вопросы по конкретным задачам, а пока меня интересует ваш опыт, почему IE обычно не работает в сценариях, которые нормально работают в Firefox.
Изменить: Спасибо за все эти отличные ответы!
Тем временем я адаптировал весь код, чтобы он также работал с Internet Explorer. Я интегрировал jQuery и теперь построил на нем свои собственные классы. Это была моя основная ошибка, я не создавал все свои вещи на jQuery с самого начала. Теперь у меня есть.
Также мне очень помог JSLint.
И помогли многие отдельные вопросы из разных ответов.
источник
Ответы:
Не стесняйтесь обновлять этот список, если вы видите какие-либо ошибки / упущения и т. Д.
Примечание. IE9 исправляет многие из следующих проблем, поэтому многое из этого применимо только к IE8 и ниже и в определенной степени IE9 в режиме совместимости. Например, IE9 поддерживает SVG,
<canvas>
,<audio>
и<video>
изначально, однако вы должны включить режим совместимости со стандартами , чтобы они были доступны.Общее:
Проблемы с частично загруженными документами: рекомендуется добавить свой JavaScript в какое-
window.onload
либо событие или подобное, поскольку IE не поддерживает многие операции с частично загруженными документами.Различные атрибуты : в CSS это
elm.style.styleFloat
в IE по сравнениюelm.style.cssFloat
с Firefox. В<label>
тегахfor
доступ к атрибуту осуществляетсяelm.htmlFor
в IE по сравнениюelm.for
с Firefox. Обратите внимание, чтоfor
это зарезервировано в IE, поэтомуelm['for']
, вероятно, лучше запретить IE создавать исключение.Базовый язык JavaScript:
Доступ к символам в строках :
'string'[0]
не поддерживается в IE, поскольку его нет в исходных спецификациях JavaScript. Использовать'string'.charAt(0)
или'string'.split('')[0]
отмечать, что доступ к элементам в массивах значительно быстрее, чем при использованииcharAt
со строками в IE (хотя приsplit
первом вызове возникают некоторые начальные накладные расходы ).Запятые в конце объектов: например
{'foo': 'bar',}
, не разрешены в IE.Проблемы, связанные с элементами:
Получение
document
IFrame :IFrame.contentDocument
(IE начал поддерживать это с версии 8. )IFrame.contentWindow.document
IFrame.contentWindow
относится кwindow
обоим браузерам.)Canvas: версии IE до IE9 не поддерживают этот
<canvas>
элемент. IE поддерживает VML, который представляет собой аналогичную технологию, а explorercanvas может предоставить оболочку на месте для<canvas>
элементов для многих операций. Имейте в виду, что IE8 в режиме соответствия стандартам работает во много раз медленнее и имеет гораздо больше сбоев, чем в режиме совместимости при использовании VML.SVG: IE9 изначально поддерживает SVG. IE6-8 может поддерживать SVG, но только с внешними плагинами, и только некоторые из этих плагинов поддерживают манипуляции с JavaScript.
<audio>
и<video>
: поддерживаются только в IE9.Динамическое создание переключателей: IE <8 имеет ошибку, из-за которой переключатели, созданные с
document.createElement
отключенным флажком, становятся недоступными. См. Также Как динамически создать переключатель в Javascript, который работает во всех браузерах? для способа обойти это.Встроенный JavaScript в
<a href>
теги иonbeforeunload
конфликты в IE: Если вhref
частиa
тега есть встроенный JavaScript (например,<a href="javascript: doStuff()">
IE всегда будет показывать сообщение, возвращенное из,onbeforeunload
еслиonbeforeunload
обработчик не был удален заранее. См. Также Запрос подтверждения при закрытии вкладки .<script>
различия событий тегов:onsuccess
иonerror
не поддерживаются в IE и заменяются специфичными для IE,onreadystatechange
которые запускаются независимо от того, была ли загрузка успешной или неудачной. См. Также « Безумие JavaScript» для получения дополнительной информации.Размер элемента / положение / прокрутка и положение мыши:
Получение размера / положения элемента : ширина / высота элементов иногда
elm.style.pixelHeight/Width
скорее в IEelm.offsetHeight/Width
, но ни одно из них не является надежным в IE, особенно в режиме причуд, и иногда один дает лучший результат, чем другой.elm.offsetTop
иelm.offsetLeft
часто неправильно сообщаются, что приводит к обнаружению неправильных позиций элементов, поэтому всплывающие элементы и т. д. во многих случаях имеют несколько пикселей.Также обратите внимание, что если элемент (или родительский элемент) имеет значение
display
из,none
то IE вызовет исключение при доступе к атрибутам размера / положения, а не возвращается,0
как это делает Firefox.Получите размер экрана (Получение видимой области экрана):
window.innerWidth/innerHeight
document.documentElement.clientWidth/clientHeight
document.body.clientWidth/clientHeight
Положение прокрутки документа / положение мыши : на самом деле это не определено w3c, поэтому нестандартно даже в Firefox. Чтобы найти
scrollLeft
/scrollTop
изdocument
:document.body.scrollLeft/scrollTop
document.documentElement.scrollLeft/scrollTop
ПРИМЕЧАНИЕ. Некоторые другие браузеры также используют
pageXOffset
/pageYOffset
.Чтобы получить позицию курсора мыши,
evt.clientX
иevt.clientY
вmousemove
событиях будет указано положение относительно документа без добавления позиции прокрутки, поэтому необходимо будет включить предыдущую функцию:Выборы / диапазоны:
<textarea>
и<input>
выбор :selectionStart
иselectionEnd
не реализованы в IE, и на его месте есть проприетарная система «диапазонов», см. также положение каретки в текстовом поле в символах от начала .Получение текущего выделенного текста в документе:
window.getSelection().toString()
document.selection.createRange().text
Получение элементов по ID:
document.getElementById
также может ссылаться наname
атрибут в формах (в зависимости от того, какой из них определен первым в документе), поэтому лучше не использовать разные элементы с одинаковымиname
иid
. Это восходит к тем временам, когдаid
w3c еще не было стандартом.document.all
( Патентованное IE-специфическое свойство ) значительно быстрее , чемdocument.getElementById
, но есть и другие проблемы , как это всегда отдает приоритетname
перед темid
. Я лично использую этот код, прибегая к дополнительным проверкам, чтобы быть уверенным:Проблемы с внутренним HTML только для чтения:
IE никак не поддерживает установки innerHTML из
col
,colGroup
,frameSet
,html
,head
,style
,table
,tBody
,tFoot
,tHead
,title
, иtr
элементы. Вот функция, которая работает с элементами, связанными с таблицами:Также обратите внимание, что IE требует добавления a
<tbody>
к a<table>
перед добавлением<tr>
s к этому<tbody>
элементу при создании usingdocument.createElement
, например:Отличия событий:
Получение
event
переменной: события DOM не передаются функциям в IE и доступны какwindow.event
. Один из распространенных способов получения события - использовать, например, значение поelm.onmouseover = function(evt) {evt = evt||window.event}
умолчанию
window.event
ifevt
undefined.Различия в коде ключевых событий: коды ключевых событий сильно различаются, хотя, если вы посмотрите на Quirksmode или JavaScript Madness , вряд ли они специфичны для IE, Safari и Opera снова отличаются.
Мышиные различия событий:
button
атрибут в IE является бит-флаг , который позволяет использовать несколько кнопок мыши сразу:var isLeft = evt.button & 1
)var isRight = evt.button & 2
)Центр: 4 (
var isCenter = evt.button & 4
)Модель W3C (поддерживаемая Firefox) менее гибкая, чем модель IE, с одновременным разрешением только одной кнопки с левым as
0
, right as2
и центром as1
. Обратите внимание, что, как упоминает Питер-Пол Кох , это очень нелогично, поскольку0
обычно означает «без кнопки».offsetX
иoffsetY
являются проблематичными, и, вероятно, лучше избегать их в IE. Более надежный способ получитьoffsetX
иoffsetY
в IE - это получить позицию относительно позиционированного элемента и вычесть ее изclientX
иclientY
.Также обратите внимание, что в IE, чтобы получить двойной щелчок по
click
событию, вам нужно зарегистрировать как событие, такclick
иdblclick
событие для функции. Firefox срабатываетclick
так же, как иdblclick
при двойном щелчке, поэтому для такого же поведения необходимо обнаружение, специфичное для IE.Различия в случае модели обработки: Оба запатентованной модели IE и модель обработки поддержки Firefox событий снизу вверх, например , если есть события в обеих элементах ,
<div><span></span></div>
тогда событий вызовут вspan
то в ,div
а не порядок , который они связаны, если использовалось традиционное, напримерelm.onclick = function(evt) {}
.«Захват» событие , как правило , поддерживается только в Firefox и т.д., которые будут вызывать
div
тоspan
событие в верхней части вниз порядок. IE имеетelm.setCapture()
иelm.releaseCapture()
для перенаправления событий мыши из документа в элемент (elm
в данном случае) перед обработкой других событий, но у них есть ряд проблем с производительностью и другими проблемами, поэтому, вероятно, следует избегать.Fire Fox:
Присоединить :
elm.addEventListener(type, listener, useCapture [true/false])
Отсоединить :
elm.removeEventListener(type, listener, useCapture)
(
type
например,'mouseover'
безon
)IE: в IE может быть добавлено только одно событие данного типа для элемента - исключение возникает, если добавлено более одного события одного и того же типа. Также обратите внимание, что это
this
относится,window
а не к привязанному элементу в функциях событий (поэтому он менее полезен):Прикрепить :
elm.attachEvent(sEvent, fpNotify)
Отсоединить :
elm.detachEvent(sEvent, fpNotify)
(
sEvent
например'onmouseover'
)Различия в атрибутах событий:
Остановить обработку событий любыми другими функциями прослушивания :
Firefox:
evt.stopPropagation()
IE:
evt.cancelBubble = true
Остановить, например, ключевые события от вставки символов или остановки флажков от проверки:
Firefox:
evt.preventDefault()
IE:
evt.returnValue = false
Примечание: Только возвращение
false
вkeydown
,keypress
,mousedown
,mouseup
,click
иreset
также предотвратить дефолт.Получите элемент, вызвавший событие:
Firefox:
evt.target
IE:
evt.srcElement
Получение элемента, от которого переместился курсор мыши:
evt.fromElement
в IE находитсяevt.target
в Firefox, если вonmouseout
событии, в противном случаеevt.relatedTarget
Получение элемента, на который переместился курсор мыши:
evt.toElement
в IE находитсяevt.relatedTarget
в Firefox, если вonmouseout
событии, в противном случаеevt.target
Примечание:
evt.currentTarget
(элемент, к которому было привязано событие) не имеет эквивалента в IE.источник
Также проверьте наличие запятых, таких как эти или подобные, если они есть в вашем коде
последняя запятая (следующая за значением2) будет разрешена Firefox, но не IE
источник
Если вы будете использовать jQuery или YUI в качестве тегов для вашего сообщения, у вас должны быть минимальные различия между браузерами ... вот для чего нужны фреймворки, чтобы позаботиться об этих кроссбраузерных различиях за вас.
Для примера посмотрите на страницу обхода quirksmode DOM , согласно которой IE не поддерживает большинство вещей ... в то время как true, фреймворки поддерживают
elem.childElementCount
, например IE не поддерживает , но в jQuery:$(elem).children().size()
работает, чтобы получить это значение, в каждом браузере. Вы найдете что-то в библиотеке для обработки 99% неподдерживаемых случаев в браузерах, по крайней мере, со сценарием ... с CSS вам, возможно, придется перейти к плагинам для библиотеки, типичный пример этого - получить закругленные углы работает в IE ... так как он не поддерживает CSS.Однако, если вы начинаете делать что-то напрямую, например
document.XXX(thing)
, тогда вы не в библиотеке, вы делаете javascript напрямую (это все javascript, но вы понимаете суть :), и это может вызвать или не вызвать проблемы, в зависимости от того, как пьяная команда IE при реализации этой конкретной функции.С IE у вас больше шансов потерпеть неудачу при правильном оформлении стиля, чем на необработанных проблемах с javascript, анимации на несколько пикселей и тому подобном, гораздо больше, конечно, в IE6.
источник
getElementbyID также будет соответствовать атрибуту name в IE, но не в других браузерах, и IE выберет то, что найдет первым.
пример:
источник
Существует множество вещей, но я попадал в одну ловушку, заключающуюся в том, что многие браузеры принимают JSON без имен в кавычках, а ie6 и ie7 - нет.
Изменить : чтобы уточнить, это проблема только тогда, когда требуется фактический JSON, а не литерал объекта. JSON - это подмножество синтаксиса объектного литерала и подразумевается как формат обмена данными (например, XML), поэтому он разработан, чтобы быть более разборчивым.
источник
Различная поддержка JavaScript
IE не поддерживает (большинство) расширений, добавленных в JavaScript с версии 1.5.
Новое в версии 1.6
indexOf()
,lastIndexOf()
,every()
,filter()
,forEach()
,map()
,some()
for each ... in
- перебирает значения вместо имен свойств.Новое в версии 1.7
[a,b] = [1,2]
let
иconst
заявленияНовое в 1.8
reduce()
,reduceRight()
Некоторые из этих вещей требуют, чтобы вы указали номер версии JavaScript для запуска (который не работает в IE), но некоторые вещи, такие как,
[1,2,3].indexOf(2)
могут показаться не такими уж важными, пока вы не попытаетесь запустить его в IE.источник
javascript
и (конкретной реализацией)JScript
, а не различий междуMozilla JavaScript(TM)
иJScript
. Было бы лучше показать, где IE отличается от ES.Основные различия между JavaScript в IE и JavaScript в современных браузерах (например, Firefox) могут быть отнесены к тем же причинам, что и различия в кроссбраузерности CSS / (X) HTML. Когда-то не было стандарта де-факто; IE / Netscape / Opera вели войну за территорию, реализуя большинство спецификаций, но также опуская некоторые из них, а также создавая собственные спецификации, чтобы получить преимущества друг перед другом. Я мог бы продолжить, но давайте перейдем к выпуску IE8: JavaScript избегали / презирали в течение многих лет, а с появлением FF и пренебрежением к webcomm IE решил сосредоточиться в основном на продвижении своего CSS с IE6. И в основном оставил поддержку DOM. Поддержка DOM в IE8 может быть такой же, как и в IE6, выпущенном в 2001 году ... так что поддержка DOM в IE почти на десять лет отстает от современных браузеров. Если у вас есть несоответствия JavaScript, характерные для механизма компоновки, лучше всего атаковать его так же, как мы взяли на себя проблемы с CSS; Ориентация на этот браузер. НЕ ИСПОЛЬЗУЙТЕ ОБРАБОТКУ БРАУЗЕРА, используйте обнаружение функций, чтобы обнаружить ваш браузер / его уровень поддержки DOM.
JScript не является собственной реализацией ECMAScript IE; JScript был ответом IE на JavaScript Netscape, оба из которых появились до ECMAScript.
Что касается атрибутов типа в элементе скрипта, type = "text / javascript" является стандартом по умолчанию (по крайней мере, в HTML5), поэтому вам никогда не понадобится атрибут типа, если ваш скрипт не является JavaScript.
Поскольку IE не поддерживает innerHTML ... innerHTML был изобретен IE и до сих пор НЕ является стандартом DOM. Другие браузеры приняли его, потому что он полезен, поэтому вы можете использовать его в разных браузерах. Что касается динамически изменяющихся таблиц, MSDN сообщает, что «из-за специфической структуры, требуемой таблицами, свойства innerText и innerHTML объектов table и tr доступны только для чтения». Я не знаю, насколько это было правдой изначально, но очевидно, что современные браузеры поняли это, имея дело со сложностями компоновки таблиц.
Я настоятельно рекомендую прочитать PPK по JavaScript Джереми Кейта « Сценарии DOM» Дугласа Крокфорда « JavaScript: хорошие части» и Кристиана Хеллмана « Начальный JavaScript с DOM-сценариями и Ajax», чтобы получить четкое представление о JavaScript.
Что касается фреймворков / библиотек, если вы еще не очень хорошо разбираетесь в JavaScript, вам следует их избегать. 2 года назад я попал в ловушку jQuery, и, хотя мне удалось добиться великолепных результатов, я ни черта не узнал о правильном кодировании JavaScript. Оглядываясь назад, можно сказать, что jQuery - это потрясающий набор инструментов DOM, но моя неспособность научиться правильным замыканиям, прототипному наследованию и т. Д. Не только вернула мои личные знания, но и моя работа начала сильно падать по производительности, потому что я понятия не имел, что я делаю.
JavaScript - это язык браузера; если вы клиентский / интерфейсный инженер, крайне важно, чтобы вы использовали JavaScript. Node.js представляет JavaScript на полную катушку, я вижу огромные успехи, предпринимаемые ежедневно в его разработке; Серверный JavaScript станет стандартом в самом ближайшем будущем. Я упоминаю об этом, чтобы еще раз подчеркнуть, насколько важен JavaScript сейчас и будет.
JavaScript вызовет больше волнений, чем Rails.
Удачного сценария!
источник
Некоторые собственные объекты доступны только для чтения, но на самом деле это не так (вы можете писать в них, но это не имеет никакого эффекта). Например, обычный расширенный JavaScript основан на расширении
Element
объекта путем переопределения системных методов, скажем, изменения Element.prototype.appendChild (), чтобы сделать больше, чем добавление дочернего узла - скажем, инициализировать его с помощью родительских данных. В IE6 это не сработает - исходный метод будет вызываться для новых объектов вместо нового.Некоторые браузеры (я не помню, какие сейчас) рассматривают новые строки между тегами HTML как текстовые узлы, а другие - нет. Таким образом, childNodes (n), nextSibling (), firstChild () и т.п. будут вести себя по-разному.
источник
Конечные запятые в массивах и объектных литералах раньше были проблемой, недавно не проверялись (имеется в виду IE8):
Это вызовет дополнительный код при создании таких структур на стороне сервера.
источник
Я только что нашел один сегодня утром, коллега установил тег сценария как:
<script type="application/javascript">
потому что его автозаполнение ide было перед "text / javascript"Но оказывается, что IE просто игнорирует весь скрипт, если вы используете «application / javascript», вам нужно использовать «text / javascript»
источник
<script>
Буквально на днях я обнаружил странную причуду с Internet Explorer. Я использовал YUI и заменил содержимое тела таблицы (), установив innerHTML
Это будет работать во всех браузерах, ЗА ИСКЛЮЧЕНИЕМ IE. Наконец я обнаружил, что вы не можете заменить innerHTML таблицы в IE. Мне пришлось создать узел с помощью YUI, а затем добавить этот узел.
Было интересно понять это!
источник
<tbody>
тегами нужно заворачивать .Раньше лишние запятые и отсутствующие запятые были обычной проблемой в IE, в то время как он плавно работает с FF.
источник
IE очень строго относится к отсутствию ";" так обычно бывает.
источник
Как бы то ни было, я столкнулся с этой неприятной проблемой в <IE9
скажем, у вас есть такой html:
и по какой-то причине (у меня был хороший) вам нужно получить весь HTML в таблице перед последним закрывающим TR, вы можете попробовать что-то вроде этого:
<IE9 здесь ничего не вернет (-1), потому что переменная tableHtml содержит все теги html в верхнем регистре, а lastIndexOf чувствителен к регистру. Чтобы обойти это, мне пришлось добавить toLowerCase () перед lastIndexOf.
источник
IE не является современным браузером и следует только за ECMAScript.
источник
Вы упомянули jQuery, с которым я менее знаком, но для общей справки, в частности с Prototype, нужно остерегаться зарезервированных слов / имен методов в IE. Я знаю, что меня часто беспокоят такие вещи, как:
someElement.appendChild(new Element('label',{ **for**: someInput.id }).update( someLabelText );
(new Element (tagName, propertyHash) - это способ создания новых элементов в Protitype). В IE
for:
должно быть'for':
, потому чтоfor
это зарезервированное слово. В этом есть смысл - но FireFox это допустит.Другой пример:
someElement.wrap('div').addClassName('someClass')
(
wrap
метод в Prototype оборачивает один элемент в другой) - В IE в текстовых областяхwrap
это свойство, и егоElement.wrap()
следует использовать вместо методизированной версииЭто два примера, которые приходят на ум из моего опыта. Они основаны на прототипе, но основная проблема не в этом: остерегайтесь любых методов / меток / идентификаторов, которые IE считает зарезервированными словами, а FireFox или Safari допускают.
источник
Дело в том, что IE не поддерживает JavaScript ... Он поддерживает свою собственную реализацию ECMAScript: JScript ... которая немного отличается ...
источник
Использование
console.log()
для вывода ошибок в консоль ошибок Firefox приведет к сбою ваших скриптов в IE. Не забудьте убрать их при тестировании в IE.источник