IE <8を含むすべてのブラウザーのDOM-shim

おはようございます。



多くのJavaScriptプログラマーは、一部のブラウザーでサポートされていないDOM JS API関数に遭遇しました(私たちは指で触れません)。 異なるブラウザー間の互換性の問題を解決するための素晴らしいライブラリes5-shimおよびDOM-shimに多くの人が精通していることは確かです。また、 DOM-shimはブラウザーをDOM4レベルに「プル」します。



この記事では、IE6およびIE7でDOM-shimを作成して、これらのブラウザーの存在を永遠に忘れる方法を説明します。



問題



言うことは何もありません。 バージョン9より前のIEは、多くの標準DOM APIをサポートしていません。



そして、 DOM-shimを使用して必要な機能を実装することでIE8を「強化」できる場合、IE6およびIE7は、残念ながら、IE <8にはNodeがないという事実により、このライブラリでサポートされません(2011 年11月 24 日発行/ 29 )。プロトタイプ。



解決策



実際、その解決策は非常に明白であり、1年前にjavascriptの学習を始めたばかりのプロジェクトで使用しました-behavior:url(.htc)[ Introduction to DHTML Behaviors ]。 しかし、ページの読み込みが本当に遅くなったため、この決定を放棄しなければなりませんでした-比較的小さなページでページが読み込まれた後、30秒待たなければなりませんでした。

しばらくして、100回ごとにビヘイビアを使用したビヘイビアでページの読み込みを高速化する方法に関する情報を偶然見つけました。lightweight = trueを追加するだけで、すべてがすぐに動作します。

IEのDOM-shimを<8にすることは難しくありません。



さあ始めましょう



最初に、元のes5-shimDOM-shimが必要です。それらを取得してやり直し、 バグ修正し、 Object.definePropertyのエミュレーションを改善します。

<...> if (!object.__defineGetter__) { if(descriptor["ielt8"]) { object["get" + property] = descriptor["get"]; object["set" + property] = descriptor["set"]; } else throw new TypeError(ERR_ACCESSORS_NOT_SUPPORTED); <...>
      
      





ERR_ACCESSORS_NOT_SUPPORTED例外をスローする代わりに、特別なフラグが存在するかどうかを確認し、存在する場合は、特別な名前でゲッターとセッターを保存します。

なぜなら IE <8ではNode.prototype(Object.definePropertyに渡される)はありません。ゲッターとセッターが蓄積する特別なオブジェクトを作成します。

 var elementProto = window.HTMLElement && window.HTMLElement.prototype || /*ie8*/window.Element && window.Element.prototype || /*ielt8*/(window["_ielt8_Element_proto"] = {});
      
      





通常どおりに送信し、「ielt8」フラグを説明に追加します

 Object.defineProperty(elementProto, "classList", {"get" : ..., "ielt8" : true}
      
      





ここで、shimライブラリのすべてのゲッターを1つのオブジェクトに収集します。 残るのは、ページ上のすべての要素に「ハング」させることだけです。

dom-shim.ielt8.htcファイルを作成します。

 <PUBLIC:COMPONENT lightWeight="true"> <PUBLIC:PROPERTY NAME="classList" GET="getClassList" /> <SCRIPT> getClassList = window._ielt8_Element_proto.getclassList </SCRIPT> </PUBLIC:COMPONENT>
      
      





ページ上のすべての要素に追加します:

 * { behavior: url(dom-shim.ielt8.htc) }
      
      





そして、それだけです。 IE6でもNode.classListができました!



以下のプロパティが同様に追加されます。



ささいなこと


1.属性を修正します。このため、htcスクリプトの開始時に元の属性を特別なコンテナーに保存します。

 if(!this._)this._={}; //Save original attributes property this._.__ielt8_attributes__=this.attributes;
      
      





そのため、IE6では、動作の実装はIE7とは異なります。IE7では、スクリプトの元のプロパティは<PUBLIC:PROPERTY NAME="attributes" GET="getAttributes" />



でオーバーライドされますが、IE6では使用できません-getAttributes getterはすぐに呼び出されます。

そのため、IE6では別のファイルを作成します。



2.すべての要素( "*")に動作を付加しないでください。 IE <8では、サポートされていない要素でハングし、エラーが発生します。 修正するには、すべてのhtmlタグをスタイルで指定するだけです。

 <style> html,body,div,span,object,iframe,h1,<... html ...>,textarea,input,select { behavior: url(dom-shim.ielt8.htc) } </style>
      
      







合計



ライブラリへのリンク: github.com/termi/ES5-DOM-SHIM

私は、 DOM-shimについて何も知らずに(そしてgithubについてさえ)過去8か月間それを開発しているという事実のために、私のDOM-shimのライブラリがDOM-shimとは非常に異なっていることに注意したい



動作するサンプルはこちらからダウンロードできます: github.com/termi/Microdata-JS (ダウンロード、examples / microdataTemplaterにアクセスし、templaterTest.htmlを開きます)

DOM-shimで起こったことを追加する提案: github.com/Raynos/DOM-shim/issues/29



更新11.27.2011:

制限事項



.htcファイルは、.htmlファイルと同じドメインに存在する必要があります。 たとえば、example.org / index.htmlファイルの場合、.htcファイルはexample.orgに、test.example.org / index.htmlファイルの場合はtest.example.orgにある必要があります。 この制限により、ライブラリの使用が大幅に複雑になります。静的サーバーに.htcファイルを置いて忘れることはできません。 サイトと同じドメインに必要なすべての.htcファイルがあることを確認してください。

同じドメインの制限

アップデート12.19.2011:

nginxプロキシ経由の同一ドメイン制限ソリューション



All Articles