0

I am writing a menu system and I need to call a function when the user clicks on a specific row. I am using new function to pass the div that called the function as well as the row the user clicked on. All well and good until I try to pass a local array to the function. If I do the following:

for (i=0;i<tmpdropnumber;i++){
    var dv=document.getElementById(id+i);
    dv.style.cursor="pointer";  
    dv.onmouseover = new Function('dropover'+"('" + id + "','" + i + "')");
    dv.onmouseout = new Function('dropout'+"('" + id + "','" + i + "')");
    dv.onclick = new Function('dropclick'+"('" + id + "','" + i + "','"+tmparray1+"','"+tmparray2+"')");
}

As you'd expect the arrays are passed as strings. I could rebuild the arrays in the function but that seems inelegant.

if I try the following:

for (i=0;i<tmpdropnumber;i++){
    var dv=document.getElementById(id+i);
    dv.style.cursor="pointer";  
    dv.onmouseover = new Function('dropover'+"('" + id + "','" + i + "')");
    dv.onmouseout = new Function('dropout'+"('" + id + "','" + i + "')");
    dv.onclick = new Function('dropclick'+"('" + id + "','" + i + "',"+tmparray1+","+tmparray2+")");
}

Trying to pass the arrays it crashes. Any ideas on how I can achieve this? I am using jquery in my code so wither a javascript or jquery solution would be fine.

9
  • Because it is using toString() when it is building the string. Commented Feb 15, 2013 at 16:02
  • 1
    in one easy word: json Commented Feb 15, 2013 at 16:02
  • I'm making a custome drop down type menu. I add a bunch of divs using a loop and attach the onclick functions when they are created. Therefore when a user clicks my function knows which row was clicked on. Always works with string just can't pass arrays (or objects) as new function only seems to pass strings. Commented Feb 15, 2013 at 16:07
  • 1
    Bondye? json? What in the world would that solve. Commented Feb 15, 2013 at 16:07
  • I do use JSON a lot in my code but for complex reasons I really need arrays at this part Commented Feb 15, 2013 at 16:08

2 Answers 2

1

Do not use new Function.

You are having problems because when the string is being built, the array is being turned into a string.

basic idea to get around the toString()

for (i=0;i<tmpdropnumber;i++){
    var dv=document.getElementById(id+i);
    dv.style.cursor="pointer";
    (function(id, i){  
        dv.onmouseover = function(){ dropover(id,i); };
        dv.onmouseout = function(){ dropout(id,i); };
        dv.onclick = function(){ dropclick(id,i, tmparray1, tmparray2); };
    })(id,i);
}

But in reality there is no need to pass in an object, id.

You can always use this to get the current row and there is rowIndex on the table. Heck you can have one event handler on the table and use handlers on the table/tbody to capture the bubbling and use target/srcElement.

Sign up to request clarification or add additional context in comments.

4 Comments

sorry. didn't explain - I'm not actually using a table. I know how to get row references for that. I need pixel perfect precision so am building a table like structure from divs
Thanks for this - looks like it is exactly what I need. I don't really understand anonymous function wrappers. Why are my variables id and i referenced after function and at the end but not the arrays?
The function that is wrapped around the event handlers forces i to not hold a reference, but rather use the value. The id probably does not have to be there either.
Id is just a variable ref to my div. don't think it needs to be there either. Thanks for your help
1

Instead of

dv.onclick = new Function('dropclick'+"('" + id + "','" + i + "','"+tmparray1+"','"+tmparray2+"')");

try

dv.onclick = function() {
    dropclick(id, i, tmparray1, tmparray2);
};

Edit

Wrap your declaration in a anonymous function:

(function(id, i) {
    dv.onclick = function() {
        dropclick(id, i, tmparray1, tmparray2);
    };
} (id, i));

2 Comments

This doesn't pick up the correct reference to i at run time. i is always shown at it's last value.
Loving the look of that - will try and let you know

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.