Callback Functions in JavaScript

来源:互联网 发布:软件接口类型主要有 编辑:程序博客网 时间:2024/05/22 02:07
from:http://www.impressivewebs.com/callback-functions-javascript/

Callback Functions in JavaScriptIf you’re fairly inexperienced with JavaScript but you’ve used jQuery, then its likely you’ve usedcallback functions. But maybe you don’t fully understand how they work or how they’re implemented.

In this post, which is based on what I’ve learned about callback functions, I’ll try to enlighten you on this fairly common JavaScript technique. And maybe some of our JavaScript experts can chime in and let me know what I’ve omitted or oversimplified.

What is a Callback Function?

The above-linked Wikipedia article defines it nicely:

A reference to executable code, or a piece of executable code, that is passed as an argument to other code.

Here’s a simple example that’s probably quite familiar to everyone, taken from jQuery:

view plain?
  1. $('#element').fadeIn('slow'function() {  
  2.     // callback function  
  3. });  

This is a call to jQuery’s fadeIn() method. This method accepts two arguments: The speed of the fade-in and an optional callback function. In that function you can put whatever you want.

When the fadeIn() method is completed, then the callback function (if present) will be executed. So, depending on the speed chosen, there could be a noticeable delay before the callback function code is executed. You can read more about jQuery’s callback functions here.

How to Write a Callback Function

If you’re writing your own functions or methods, then you might come across a need for a callback function. Here’s a very simple example of a custom callback function:

view plain?
  1. function mySandwich(param1, param2, callback_fun) {  
  2.     alert('Started eating my sandwich.\n\nIt has: ' + param1 + ', ' + param2);  
  3.     callback_fun();  
  4. }  
  5.   
  6. mySandwich('ham''cheese'function() {  
  7.     alert('Finished eating my sandwich.');  
  8. });  

Here we have a function called mySandwich and it accepts three parameters. The third parameter is the callback function. When the function executes, it spits out an alert message with the passed values displayed. Then it executes the callback function.

Notice that the actual parameter is just “callback” (without parentheses), but then when the callback is executed, it’s done using parentheses. You can call this parameter whatever you want, I just used “callback” so it’s obvious what’s going on.

The callback function itself is defined in one the third argument passed to the function call. That code has another alert message to tell you that the callback code has now executed. You can see in this simple example that an argument passed into a function can be a function itself, and this is what makes callbacks possible in JavaScript.

Here’s a JSBin that uses the simple example above.

Make the Callback Optional

One thing you’ll notice about jQuery callbacks is that they’re optional. This means if a method accepts a callback, it won’t return an error if a callback is not included. In our simple example, the page will return an error if we call the function without a callback, like this:

view plain?
  1. function mySandwich(param1, param2, callback) {  
  2.     alert('Started eating my sandwich.\n\nIt has: ' + param1 + ', ' + param2);  
  3.     callback();  
  4. }  
  5.   
  6. mySandwich('ham''cheese');  

You can see this in action here. If you open your developer tools, you’ll see an error that says “undefined is not a function” (or something similar) that appears after the initial alert message.

To make the callback optional, we can just do this:

view plain?
  1. function mySandwich(param1, param2, callback) {  
  2.     alert('Started eating my sandwich.\n\nIt has: ' + param1 + ', ' + param2);  
  3.     if (callback) {  
  4.         callback();  
  5.     }  
  6. }  
  7.   
  8. mySandwich('ham''cheese');  

Now, since we’re checking to ensure the existence of callback, the function call won’t cause an error without it. You can test this example here.

Make Sure the Callback is a Function

Finally, you can ensure that whatever value is passed as the third argument is in fact a proper function, by doing this:

view plain?
  1. function mySandwich(param1, param2, callback) {  
  2.     alert('Started eating my sandwich.\n\nIt has: ' + param1 + ', ' + param2);  
  3.     if (callback && typeof(callback) === "function") {  
  4.         callback();  
  5.     }  
  6. }  
  7.   
  8. mySandwich('ham''cheese''vegetables');  

Notice that the function now includes a test using the typeof operator, to ensure that whatever is passed is actually a function. The function call has a third argument passed, but it’s not a function, it’s a string. So the test usingtypeof ensures no error occurs.

Here’s a JSBin with a nonfunction argument passed as the callback.

A Note About Timing

Although it is true that a callback function will execute last if it is placed last in the function, this will not always appear to happen. For example, if the function included some kind of asynchronous execution (like an Ajax call or an animation), then the callback would execute after the asynchronous action begins, but possibly before it finishes.

Here’s an example that uses jQuery’s animate method:

view plain?
  1. function mySandwich(param1, param2, callback) {  
  2.     alert('Started eating my sandwich.\n\nIt has: ' + param1 + ', ' + param2);  
  3.   
  4.     $('#sandwich').animate({  
  5.         opacity: 0  
  6.     }, 5000, function() {  
  7.         // Animation complete.  
  8.     });  
  9.   
  10.     if (callback && typeof(callback) === "function") {  
  11.         callback();  
  12.     }  
  13. }  
  14.   
  15. mySandwich('ham''cheese'function() {  
  16.     alert('Finished eating my sandwich.');  
  17. });  

And again here’s that code live.

Notice that although the callback appears later in source order than the animation, the callback will actually execute long before the animation completes. In this case, solving this problem is easy: You just put the callback execution inside theanimate method’s callback function (where it says “Animation complete”).

This doesn’t cover all the details regarding asynchronous functions, but it should serve as a basic warning that callback functions will only execute last as long as all the code in the function is synchronous.

Anything to Add?

For most JavaScript junkies, this is probably pretty easy stuff. So forgive me if you were expecting something deeper — this is the best I can do. :) But if you have anything else to add or want to correct anything I’ve said, please do so.

原创粉丝点击