Why can't I use onClick to execute a function inside a jQuery $(document).ready function?

I'm new to Javascript and jQuery. I want to click a button and have a js function executed. (For this example, it's just an alert, but it's actually an ajax function.)

The first alert appears, but after I click the button, I never see the second ("did it") alert. It looks like javascript doesn't think the doIt() function is defined when the button is clicked.

Here's the relevant code:

$(document).ready(function()
{ 
    alert('ready');

    function doIt() {
        alert('did it');
    };
}
)

<body>
    <input name="Go" type="button" value="Go" onclick="doIt();"/>
</body>

It's because that function isn't in a global context, which is where your onclick="" is looking for it. You need to move it outside your document.ready (so it's not scoped exclusively to that closure), or (a better approach IMO) bind it inside the document.ready, here's what I mean by each:


Binding it inside (remove your onclick="" for this):

$(document).ready(function() { 
  alert('ready');
  $("input[name='Go']").click(doIt);
  function doIt() {
    alert('did it');
  }
});

or the anonymous version (again remove your onclick=""):

$(document).ready(function() { 
  alert('ready');
  $("input[name='Go']").click(function() {
    alert('did it');
  });
});

Or move it outside (keep your onclick=""):

$(document).ready(function() { 
  alert('ready');
});
function doIt() {
  alert('did it');
}

You define doIt in your document.ready as a function statement.

Either you should use a function expression or declare the function out of the ready function.

$(document).ready(function()
{ 
    alert('ready');

    doIt = function() { //now has global scope.
        alert('did it');
    };
}
)

<body>
    <input name="Go" type="button" value="Go" onclick="doIt();"/>
</body>

(yes, the onClick is not really the jQuery way of doing it and probably should be replaced by a click handler defined in the ready function, but it works and is allowed.


What you need to do is bind a "click" event to it using jquery like this.

jQuery(document).ready(function($) {

    $('#my_button').click(function() {

        alert('i was clicked');

    });
});  

<input type="button" id="my_button" value="Go" />

Here is a live jsfiddle demo for you: http://jsfiddle.net/8A5PR/

Here is the manual page for you: http://api.jquery.com/click/


Javascript has two kinds of scope, global, and function level. If you declare doIt inside a function, it will not be visible outside the function. There are a few ways to fix it

//just declare the function outside the ready function
$(function() {
});
function doIt() { alert('did it'); }

//decare a variable outside the function
var doIt;
$(function() {
  doIt = function() { alert('did it'); }
});

// if you dont use var, variables are global
$(function() {
  doIt = function() { alert('did it'); }
})

$(document).ready(function() 
{ 
});

is an event handler for document.ready, the functions inside that handler are within that scope.

A better method is to insert a handler for your click event inside, then call that function there.

$(document).ready(function() 
{  
    alert('ready'); 

  $('body input').click(function(){
    doIt();
  });
   function doIt() { 
        alert('did it'); 
    }; 
});

This ALSO has the side effect of removing code from your markup (a good thing) in that you can remove that onclick from your input tag.