繁体   English   中英

动态定义硬编码的Javascript函数

[英]Defining a hardcoded Javascript function dynamically

我正在为数据库应用程序编写Web前端。 我在html主体中有几个函数调用,例如:

<input type=button value="Set 1" id="btn1" onClick=edit_entry(this,"edit","title")>
<input type=button value="Set 2" id="btn2" onClick=edit_entry(this,"edit","name")>
<input type=button value="Set 3" id="btn3" onClick=edit_entry(this,"edit","gender")>

function edit_entry(src, action, arg1) {
  alert(src.onclick);
  src.onclick = function () { edit_entry( src, action, arg1 };
  alert(src.onclick);
}

当单击“ btn1”时,第一个警报返回硬编码的函数定义: function onclick(event) { edit_entry(this,"edit","title") }

但是第二个警报返回带有变量的函数定义function onclick(event) { edit_entry(src, action, arg1) }

因此,当这些变量以后更改时,该函数的确会获得错误的值。 我如何将变量的内容而不是变量本身应用于函数定义,以使该定义再次成为function onclick(event) { edit_entry(this,"edit","title") }

PS:我知道此代码段没有任何意义,因为它只能尽可能简单地描述我的问题。


这是我指的代码。 我希望这一切现在变得更有意义。 抱歉给你带来不便。

HTML正文:

<input type="button" value="Edit" id="group_1_button_edit" class="action_element" onClick=edit_entries(this,"edit","artnr","artalt","bez1","bez2","bez3")>
<input type="button" value="Edit" id="group_9_button_edit" class="action_element" onClick=edit_entries(this,"edit","dok1","dok2","dok3","dok4","dok5")>

“ edit”后面的值是将从中读取内容的输入文本框的ID。

function edit_entries(caller,action,opt1,opt2,opt3,opt4,opt5,opt6,opt7,opt8,opt9,opt10,opt11,opt12) {

caller_id = caller.id.split("_");
id = caller_id[1];

switch(action) {
    case "edit":

        //Making textboxes writeable for changing values
        //[...]

        document.getElementById("group_"+id+"_button_edit").value="Save";
        document.getElementById("group_"+id+"_button_edit").onclick=function(){ edit_entries(this,"save",opt1,opt2,opt3,opt4,opt5,opt6,opt7,opt8,opt9,opt10,opt11,opt12); };
    break;
    case "save":
        if (confirm("Datensatz wirklich aktualisieren?")) {
            artnr_key = XML_OBJ.getElementsByTagName("artnr")[0].textContent;

            string = "";
            //Building the AJAX Request String: textbox id = value
            url = 'mysql_req_n1.php?type=edit_entries&'+string;
            send_request(url);
        }
    break;
}
}

//called by AJAX handler
function edit_entries_unlock() {

//Getting "id" by value check
counter_a = 1;
while (counter_a <= 9) {
    if (document.getElementById("group_"+counter_a+"_button_edit").value == "Save") id = counter_a;
    counter_a++;
}


//Getting textbox IDs located in the AJAX response
opts = XML_OBJ.getElementsByTagName("opts")[0].textContent;
options = opts.split(",");

//Making textboxes readonly again
//[...]

document.getElementById("group_"+id+"_button_edit").value="Edit";
document.getElementById("group_"+id+"_button_edit").onclick=function(){ edit_entries(this,"edit",options[0],options[1],options[2],options[3],options[4],options[5],options[6],options[7],options[8],options[9],options[10],options[11]); };

}

就是这样:

我单击第一个按钮(group_1_button_edit)。 它跳到切换块“ edit”,使文本框可写,并将edit按钮更改为save按钮。 工作正常。

我点击保存。 开关块“保存”构建请求字符串并启动ajax请求。

响应在那里时,ajax处理程序将启动edit_entries_unlock()。 XML响应的一部分是我以前使用的文本框ID。 onclick函数再次更改为带有XML对象中相应文本框ID的“编辑”函数。

现在,我单击第二个按钮“ group_9_button_edit”。 一切都如上所述工作。 没问题。 第9组的文本框将解锁,然后根据需要保存并再次锁定。

但是现在有一个错误:我再次单击第一个按钮“ group_1_button_edit”,该按钮现在使用更改后的函数定义。 它以“ GROUP 9”(我之前编辑过)而不是“ GROUP 1”的文本框ID的值启动开关块“ edit”。

我想这与变量opt1-opt12有关。 它们始终包含最后一次“ edit_entries_unlock()”运行的值。 而且,由于所有已编辑的函数定义也都使用opt1-opt12,因此它们均以上次运行的值开头,而不是以我在重新创建函数定义时使用的值开头。

因此,我问如何在函数创建过程中而不是在执行过程中使用变量的内容来构建函数定义。

我希望现在更有意义。 很抱歉,无法显示文字。

这是一种非常糟糕的数据传递方式。

您应该避免使用内联代码

<input type=button value="Set 1" id="btn1" onClick=edit_entry(this,"edit","title")>
<input type=button value="Set 2" id="btn2" onClick=edit_entry(this,"edit","name")>
<input type=button value="Set 3" id="btn3" onClick=edit_entry(this,"edit","gender")>

应该

<input type=button value="Set 1" id="btn1" data-field-name="title">
<input type=button value="Set 2" id="btn2" data-field-name="name">
<input type=button value="Set 3" id="btn3" data-field-name="gender">
<script>
(function(){  // or use on load event

    // define the click function
    var clickFunction = function(event){  
        // get the element data
        var fieldName = event.target.attributes["data-field-name"].value;
        // do what you need to do.....
    }

    // query the DOM to get the elements you are after.
    var el = document.getElementsByTagName("input");

    // iterate them and add the event handler to each.
    for(var i = 0; i < el.length; i++){
         el[i].addEventListener("click",clickFunction,false);
    }
})();
</script>

至于您尝试在示例中给出的内容,我没有任何线索,所以也许这会对您有所帮助。

您的onclick处理程序将创建一个闭包 因此,下面(来自edit_entry函数)中的值srcactionarg1将是创建/重新创建此函数时的值(后者是您下次单击时的值)

src.onclick = function () { edit_entry( src, action, arg1 };

您将只能在同一方法(或它的子方法)中修改它们。 请注意,由于您将onclick设置为上述内容,因此下次单击时,基本上会将相同的变量传递到处理程序中。

您对这些变量看到的任何更改都将在您的onclick处理程序中进行(而不是在其外部)

最终,在TJCrowder的帮助下,我得以修复了代码。 我需要修复的行是

options = opts.split(",");

var options = opts.split(",");

我不知道在不带var的函数中声明变量将使它们成为window对象的一部分,因此使其成为全局变量。 因此,我的关闭工作是访问全局变量而不是局部变量。

一句话,但影响很大。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM