2012-03-13 12 views
0

ここでは、理想的なことが起こっています。率直に言ってjQueryを使っていますが、これは私がかなり慣れていないので、これは自分の初心者のアイムです。jQuery:ループ内の間違った要素にイベントがバインドされています

設定オブジェクトを関数に送信します。この設定オブジェクトは、 "関数"の名前で構造体を含みます。この "関数"オブジェクトは、jQuery識別子がキーで、値がコールバック関数である構造体です。

次に、target-functionが送信されるtarget関数でsettings.functionsオブジェクトを繰り返し実行して、各関数をそれぞれのターゲットにバインドします。

しかし、$ button.click()イベントは常にすべてのコントロールを最後のsettings.functions関数に設定します。

「削除」と「編集」の2つのボタンがあり、設定オブジェクトを設定して、それぞれが独自の機能を取得するように設定しています...そのため、両方のボタンに「編集」機能が表示されます。テストでは、キーに関係なく、両方のボタンが常にsettings.functions構造体の最後の関数を取得することが示されています。

"this.init = function ..."というコードは、奇妙さの中心を参照してください。 (途中でスニペット)

私がこのようにしている理由は、コールバック関数(settings.functionsで設定されている)が$ resourcesの中から$ resource要素にアクセスする必要があるからです。 each()節。つまり、ライブラリ関数の中から$リソースオブジェクトをコールバックに返す必要があります。

はここで関数を呼び出す部分です:


$(document).ready(function() { 

    var settings = { 
     functions: { 
      ".but-act-delete": function($row) { 
       if (confirm("Are you sure you want to delete this resource? This action cannot be undone!")) { 
        /* Nevermind this 
        $page_action.val("resource-delete"); 
        $resource_id.val($row.attr("resource_id")); 
        $page_form.submit(); 
        */ 
       } 
      }, 
      ".but-act-edit": function($row) { 
       window.location = "admin-resource-edit.php?resource_id=" + $row.attr("resource_id"); 
      } 
     } 
    }; 

    var supertable = new SuperTable(); 
    supertable.init(settings); 
}); 

は、ここでライブラリ関数です:ここで


this.init = function(settings) 
{ 
    var $resources = $("td.act"); 
    $resources.each(function(index, resource) 
    { 
     var $resource = $(resource); 

     var button_class; 
     for (button_class in settings.functions) 
     { 
      var $button = $resource.find(button_class); 

      // This accurately shows ".but-act-edit" or ".but-act-delete" 
      alert(button_class); 

      $button.click(function() 
      { 
       // This ALWAYS shows ".but-act-edit" 
       alert(button_class); 

       // Find the proper callback. 
       var func = settings.functions[button_class]; 

       // Call the call-back with the required element $resource. 
       func($resource); 
      }); 
     } 
    }); 
} 

は、問題のHTMLです。


<td class="act" resource_id="<?php print $resource_id; ?>"> 
    <input type="button" class="but-act-edit" /> 
    <input type="button" class="but-act-delete" /> 
</td> 

それは$のbutton.clickを()が表示されますが、それは一つだけ入力するたびに(返す$ resource.find(button_class)で見つかったすべてのボタンにイベントハンドラたびに、1つだけでなくを割り当てそれはすべきである)。

ご協力いただきありがとうございます。特に私がしていることを不要にする方法があれば。

ありがとうございます。

答えて

2

これは古典的な「コールバックで外部ループ変数を使用する」問題です。

button_class変数がループ内で変更されますが、コールバックで正しくバインドされないため、最終値が常に使用されます。

$.each(settings.functions, function(button_class, func) { 
}) 

の代わりに::

for (button_class in settings.functions) 

これはあなたのbutton_class変数が正しくそれぞれの可能な値のためにバインドされていることを保証します

この場合、最も簡単な修正は使用することです。

+0

イェーイ、それが動作するようになりました! :) どうもありがとう! 問題を理解するために私がチェックアウトすることを特にお勧めできるものはありますか? - 私はまだそれが失敗した理由についての論理を得ていない。しかし、それは今、再びありがとう! – Teekin

+1

@HelgiHrafnGunnarssonそこには同様の質問の_dozens_があります。 'javascript loop variable callback'のようなもののためのGoogle。 – Alnitak

+0

よろしくお願いします。 – Teekin

0

しかし、私はあなたが達成しようとしているものを理解している場合、あなたはこのように、あなたのロジックを簡素化することができると思います...

$("td.act").find(":input").click(function(event) { 

    var _name = $(event.currentTarget).attr('class'); 

    if (_name) { 
     alert(_name); 
    } 

});​ 
+0

いいえ、それは主要な成分である$ resource変数を投げ戻しています。だから、私は長い道のりを行く。私はコードを短くする方法があると確信しています。 – Teekin

関連する問題