101

With jQuery code like:

$("#myid").click(myfunction);

function myfunction(arg1, arg2) {/* something */}

How do I pass arguments to myfunction while using jQuery?

alex
  • 479,566
  • 201
  • 878
  • 984
  • Possible duplicate of [Passing a function with parameters as a parameter?](http://stackoverflow.com/questions/1300242/passing-a-function-with-parameters-as-a-parameter) – Michał Perłakowski Jan 02 '16 at 14:37

6 Answers6

122

The simplest way is to do it like so (assuming you don't want any of the event information passed to the function)...

$("#myid").click(function() {
    myfunction(arg1, arg2);
});

jsFiddle.

This create an anonymous function, which is called when the click event is triggered. This will in turn call myfunction() with the arguments you provide.

If you want to keep the ThisBinding (the value of this when the function is invoked, set to the element which triggered the event), then call the function with call().

$("#myid").click(function() {
    myfunction.call(this, arg1, arg2);
});

jsFiddle.

You can't pass the reference directly in the way your example states, or its single argument will be the jQuery event object.

If you do want to pass the reference, you must leverage jQuery's proxy() function (which is a cross browser wrapper for Function.prototype.bind()). This lets you pass arguments, which are bound before the event argument.

$("#myid").click($.proxy(myfunction, null, arg1, arg2));   

jsFiddle.

In this example, myfunction() would be executed with its ThisBinding intact (null is not an object, so the normal this value of the element which triggered the event is used), along with the arguments (in order) arg1, arg2 and finally the jQuery event object, which you can ignore if it's not required (don't even name it in the function's arguments).

You could also use use the jQuery event object's data to pass data, but this would require modifying myfunction() to access it via event.data.arg1 (which aren't function arguments like your question mentions), or at least introducing a manual proxy function like the former example or a generated one using the latter example.

alex
  • 479,566
  • 201
  • 878
  • 984
  • 2
    keep in mind, you'll lose the jquery context $(this) in myfunction(). To maintain, call `myfunction(this, arg1, arg2)` from the anonymous handler. Then your function can do `myfunction(el, arg1, arg2) { alert($(el).val()); }` – lambinator Oct 11 '11 at 16:41
  • 11
    @geosteve: If you wanted to keep it, use `myfunction.call(this, arg1, arg2)`. – alex Oct 11 '11 at 22:57
  • 1
    That's not passing arguments to the function, as the question asks. It's calling a function that calls another function. Nesting functions inside anonymous functions is not a good idea as you can't unbind the anonymous function easily. – George Filippakos Jun 01 '13 at 09:40
  • 1
    @geo1701 You can if you use a custom namespace and only bind once to it. For most purposes, it's OK. But you do lose that benefit that you mentioned. – alex Jun 01 '13 at 12:20
  • 1
    Agreed with @geo1701, I had to remove event handler and his solution is only one that worked. – Pavel K Jan 25 '14 at 08:12
  • @alex can you tell me how to do this in a structure with classes? : `function FancyScroll() {this.version = '1.0'; this.click = function() {console.log(this.version)}; $('#id').on('click', $.proxy(this.click, this)) } var fs = new FancyScroll();` http://jsfiddle.net/hqduwqe0/- better to read – Mephiztopheles Nov 14 '14 at 10:55
  • This is the first time `$.proxy` has ever seemed clear to me. Thank you very much! – dgo Dec 26 '17 at 22:59
  • Great answer. BTW, you can also use: $("#myid").click({arg1: "foo", arg2: "bar"}, myfunction). And the listener would look like: function myfunction(event){ alert(event.data.arg1); alert(event.data.arg2); } – Leo Aug 09 '18 at 14:34
  • This is not at all the correct answer. It is also in no way the easiest solution and it is misleading. The solution proposed by @GeorgeFilippakos is what yo will get straight for the jQuery documentation. – asiby Dec 14 '18 at 21:51
89
$("#myid").on('click', {arg1: 'hello', arg2: 'bye'}, myfunction);

function myfunction(e) {

    var arg1 = e.data.arg1;
    var arg2 = e.data.arg2;

    alert(arg1);
    alert(arg2);

}

//call method directly:
myfunction({
    arg1: 'hello agian', 
    arg2: 'bye again'
});

Also allows you to bind and unbind specific event handlers using the on and off methods.

Example:

$("#myid").off('click', myfunction);

This would unbind the myfunction handler from #myid

George Filippakos
  • 16,359
  • 15
  • 81
  • 92
  • That's not passing arguments to the function, as the question asks. – alex May 29 '13 at 00:14
  • 5
    That is how you pass arguments (you wrap them inside an object). – George Filippakos May 30 '13 at 08:19
  • It's how you pass data, but it's a stretch calling them function arguments. – alex May 30 '13 at 10:14
  • 7
    It's a better solution to the accepted answer as it uses the recommended pattern of binding and unbinding listeners using the On/Off methods. – George Filippakos Jun 01 '13 at 09:45
  • 7
    If you think unbinding is quite rare then you must have very limited experience. Please don't poo poo contributions from others - this is a collective knowledge base not a competition. There are no right or wrong answers. – George Filippakos Jun 02 '13 at 20:15
  • This is what i'm using, it works on dinamically created elements, so to me it´s a much better awnser than the accepted one! – Nmaster88 Jan 12 '17 at 11:39
  • How can we use this with event delegation syntax having css selector. `$('#parent').off('click', '.child-dynamc').on('click', '.child-dynamc',{arg1: 'hello', arg2: 'bye'}, myfunction);` – Rohith K P Jun 06 '17 at 21:02
  • Great answer. BTW, you can also use: $("#myid").click({arg1: "foo", arg2: "bar"}, myfunction). And the listener would look like: function myfunction(event){ alert(event.data.arg1); alert(event.data.arg2); } – Leo Aug 09 '18 at 14:34
  • This is my best answer for me. Just want to point out the "call method directly" code is missing the data property: `//call method directly: myfunction({ data: { arg1: 'hello agian', arg2: 'bye again' } });` – Harry Oct 15 '19 at 08:50
  • Thanks, this is will be very useful. – Goran Usljebrka Dec 17 '19 at 10:06
12

while you should certainly use Alex's answer, the prototype library's "bind" method has been standardized in Ecmascript 5, and will soon be implemented in browsers natively. It works like this:

jQuery("#myid").click(myfunction.bind(this, arg1, arg2));
Breton
  • 15,401
  • 3
  • 59
  • 76
  • 2
    Will `this` be set to a different context if you use this method, for example, `bind()`ing it to `this` in that context (global) may result in that click handler having the `window` object as `this` as opposed to a reference to the `#myid` element? – alex Oct 27 '11 at 23:54
  • 2
    @alex you are quite right. jQuery will bind the #myid element to 'this' in its event handlers, and using the bind method will override that. I wrote this post several years ago it would seem so it's hard to say what I was thinking at the time. I guess I just assume that the people reading my answers are smart enough to figure these details out themselves. – Breton Oct 28 '11 at 03:46
  • 12
    That is a very dangerous assumption. – Travis Nov 14 '11 at 23:10
  • @Travis As of this writing, (almost 11 years after Breton's answer), caniuse.com reports Ecmascript 5 is supported by **98.87%** of the browsers. (see https://caniuse.com/#search=ECMAScript%205) – Stephan May 18 '20 at 09:18
  • 1
    @Stephan My tongue-in-cheek comment was aimed at @Breton for assuming `people reading my answers are smart enough to figure these details out themselves`, not about Ecmascript. – Travis Jul 19 '20 at 18:13
7

There are great answers already, but anyway, here are my two cents. You can also use:

$("#myid").click({arg1: "foo", arg2: "bar"}, myfunction)

And the listener would look like:

function myfunction(event){ alert(event.data.arg1); alert(event.data.arg2); }

Leo
  • 409
  • 6
  • 7
6

Old thread, but for search purposes; try:

$(selector).on('mouseover',...);

... and check out the "data" parameter: http://api.jquery.com/on/

e.g.:

function greet( event ) {
  alert( "Hello " + event.data.name );
}
$( "button" ).on( "click", {name: "Karl"}, greet );
$( "button" ).on( "click", {name: "Addy"}, greet );
dhc
  • 647
  • 8
  • 17
2

Simple:

$(element).on("click", ["Jesikka"],  myHandler);

function myHandler(event){
   alert(event.data);     //passed in "event.data"
}
T.Todua
  • 53,146
  • 19
  • 236
  • 237