9

アイテムの追加や削除など、HTML フォーム内のアイテムのリストを編集できるように、いくつかの JavaScript を作成しました。Firefoxで動作するようになりました。Internet Explorer で試してみると、追加された項目がフォームと共に送信されていないことがわかりました。

簡単に言えば...多くの単純化、デバッグ、IEが新しいフォーム入力を無視するようにトリガーしている行を見つけました。したがって、動作の問題は解決されます。

しかし今、私は尋ねなければなりません:なぜですか?これはIEのバグですか?

簡略化されたコードは次のとおりです。

<html>
<head>
    <title>Test</title>
    <script type="text/javascript">
        function add() {
            div = document.getElementById("mylist");

            // *** Adding text here works perfectly fine. ***
            div.innerHTML += " ";

            e = document.createElement("input");
            e.setAttribute("type", "text");
            e.setAttribute("name", "field3");
            e.setAttribute("value", "--NEWVALUE--");
            div.appendChild(e);

            // *** Adding text here works perfectly fine in Firefox, but for
            //     Internet Explorer it causes field3 to not be submitted. ***
            //div.innerHTML += " ";
        }
    </script>
</head>
<body>
    <form action="" method="get">
        <div id="mylist">
            <input type="text" name="field1" value="value1" />
            <input type="text" name="field2" value="value2" />
        </div>
        <a href="javascript:" onclick="add()" />Add</a>
        <input type="submit" value="Submit" />
    </form>
</body>
</html>

それを試すには、当然のことを行います。IE をロードし、[追加] をクリックし、[送信] をクリックして、アドレス バーの内容を確認します。の最後の行のコメントを外すとadd()、IE はレポートを突然停止しfield3ます。Firefox ではどちらの方法でも問題なく動作します。

何か案は?好奇心旺盛な心は知りたがっています。(そして、必要に応じて移植可能な方法でそこにテキストを追加して、IE が満足するようにするにはどうすればよいでしょうか?)

4

3 に答える 3

7

これはIEのバグですか?

そうらしい。DOM メソッドを使用して <input> 要素を作成する場合、IE は 'name' 属性を正しく取得しません。要素がサブミットするという点ではそこそこですが、要素の「innerHTML」表現を取得しようとすると、不思議なことに消えてしまいます。これは、innerHTML に直接記述して要素を作成した場合には発生しません。

また、'myform.elements.x.value' などの DOM レベル 0 フォーム ナビゲーション メソッドを使用する場合、'elements' 配列を介したアクセスは機能しない可能性があります (同様に、直接の 'my​​form.x' アクセスを誤って使用する人もいます)。いずれにせよ、最近は getElementById() を好むかもしれません。

したがって innerHTML を使用する、DOM メソッドを使用してください。フォーム フィールドを作成するときにそれらを混在させないことをお勧めします。

これは文書化され (「備考」を参照)、最終的に IE8 で修正されました。

いずれにしても、次のことは絶対にしないでください。

div.innerHTML+= '...';

これは、次の構文シュガーにすぎません。

div.innerHTML= div.innerHTML+'...';

つまり、要素の子 HTML コンテンツ全体をシリアル化し、文字列を連結してから、新しい文字列を再解析して要素に戻し、元のコンテンツをすべて破棄する必要があります。つまり、シリアル化できないものはすべて失われます。また、IE の偽の半分作成された「名前」属性も失われます。これは、JavaScript イベント ハンドラー、DOM リスナー、または各子要素にアタッチしたその他のカスタム プロパティも意味します。また、不必要なシリアル化/解析サイクルが遅くなります。

于 2009-03-04T19:36:13.670 に答える
3

bobinceとlevikに答えてくれてありがとう。それらといくつかの実験を使用して、ここに私の結論があります:

  1. はい、IEのバグです。

  2. IE 8は、 Microsoftによると、バグを修正します。「Internet Explorer 8以降では、createElementメソッドで動的に作成された要素に実行時にNAME属性を設定できます。」

  3. バグはこれです:種類e.setAttribute("name", "field3")のみを呼び出すと名前が設定されます。要素に他に何も起こらなければ機能しますが、シリアル化を要求された場合、名前はシリアル化されません。それで、私がそれが名前を失ったシリアル化を強制したと言ったとき、それは逆シリアル化で回復されませんでした。名前なし、フォーム送信への包含なし。innerHTML += " "

  4. 回避策#1:e = document.createElement("<input name='field3' />")シリアル化に直面した場合でも機能します。

  5. 回避策#2:innerHTML + =を使用してテキストを追加するのではなく、次のようなテキスト要素を追加できますdiv.appendChild(document.createTextNode(" "));。私はテキストを追加するより良い方法があるに違いないと思っていました、そして今私はそれを知っています:-)。

乾杯、
-jsf

于 2009-03-04T20:26:41.117 に答える
3

IE は、実行時にいくつかの組み込みプロパティを変更することに非常にうるさいです。たとえば、設定中に入力要素の名前を変更することはできません。

私があなただったら試してみたい2つのこと:

  1. を使用する代わりに、およびプロパティを明示的にsetAttribute()設定してみてください。nametypevalue

    e.name = "text";

  2. これが機能しない場合は、これらすべての属性をdocument.createElement()呼び出しに含める必要がある場合があります。

    var e = document.createElement("<input type='text' name='field'>");

    これにより、一部のブラウザーでは実際に例外がスローされる場合があります。したがって、最適なクロスブラウザの方法は次のとおりです。

.

var e;
  try {
    e = document.createElement("<input type='text' name='field'>");
  } catch (ex) {
    e = document.createElement("input");
    e.type = 'text';
    e.name = 'field';
  }
  e.value = 'value';
于 2009-03-04T19:02:59.787 に答える