5

Is there a way to include a javascript file only once or declare a function only once? The issue I am having is that I have an HTML module that contains a javascript include. Well this module is loaded in a loop, and therefore that file is loaded multiple times. I've worked out most of the kinks, but what bothers me is that I know the same function is getting created multiple times, and this look can be as many as 30 iterations. To me, I don't like the fact that the same function is getting created over and over. Should I care? Is there a way I can prevent this? I know I can detect when a function exists, can I put the function declaration in between an if statement?

Update

I've tried out one of the suggestions:

if(typeof btnSendInvite_click != 'function')
{
    function btnSendInvite_click()
    {
        alert("#invite_guest_" + $(this).attr("event_id"));
        return false;
    }
}

but that doesn't work. I've also tried

if(!btnSendInvite_click)
    {
        function btnSendInvite_click()
        {
            alert("#invite_guest_" + $(this).attr("event_id"));
            return false;
        }
    }

but it doesn't work. What happens is that I have this line:

$(document).ready(function()
                    {
                        $(".btnSendInvite").bind("click", btnSendInvite_click);
                    });

and when the button gets clicked, that functions is executed six times, which is the amount of times that the file was included which tells me that the function is being created multiple times... I think.

Update

So after a lot of struggling, this problem is turning into something different than what I thought. The bind is being called multiple times, so it's getting bound multiple times, and therefore calling the function multiple times. I guess my next question is, is there a way to bind a function to a control only once? I've tried the jquery "one" already and it doesn't work.

3
  • 2
    no, what you have shown is that the function is called not created 6 times. put the alert in the if statement but outside the function definition to see an alert each time the function is defined Commented Nov 25, 2010 at 17:02
  • For calling bind only once, see my post ("edit 2") Commented Nov 25, 2010 at 17:16
  • @tobyodavies - you're right. I was so caught up in the redeclaration that I wasn't thinking straight. that 6 alerts was showing me nothing except that I was binding 6 times. Commented Nov 25, 2010 at 17:22

3 Answers 3

4

Yes, you can (run on jsfiddle).

if (!window.myFunction) {
    window.myFunction = function() {
        //...
    }
}

Edit: In your case it would be:

if (!window.btnSendInvite_click) {
  window.btnSendInvite_click = function() {
    alert("#invite_guest_" + $(this).attr("event_id"));
    return false;
  }
}

The call to bind() also has to be somewhere in that conditional block.

Note: The following variant won't work, at least not on all browsers:

if (!window.myFunction) {
  function myFunction() {
    //...
  }
}

Edit 2: For your update:

Declare a variable when you call bind.

if (window.iBoundThatStuff!=true) {
    iBoundThatStuff=true;
    //call bind() here
}
Sign up to request clarification or add additional context in comments.

3 Comments

I've found that if you don't use typeof, on firefox it gives a javascript error: btnSendInvite_click is not defined and breaks the rest of the script.
@JohnathanKong: What about if (window.myFunction==undefined) {?
You were right. I was missing something around my bind, or in my case, something before it. What I had to do was unbind all handlers, then rebind it once. My code ended up being $(".btnSendInvite").unbind("click"); $(".btnSendInvite").bind("click", btnSendInvite_click);
1

Having JS included in a loop is ridiculous. Move your JS out of the loop. JS can tell if function was defined but fixing bad server side loop in JS is definitively a bad practice.

3 Comments

I agree with you, but these are modules, so I can't really move them out. I know it's bad practice and that's why I'm trying to correct it now as best as I can.
OK got it. You can use some kind of a const variable that if defined bypasses rest of the code. With this approach you don't have to check existence of all functions. Happy coding ;)
I was thinking about that, but these modules are supposed to be self-contained, so they should not know of anything outside of their world which makes it that much harder.
0

Yes you should worry about not including your script file several times and not to declare the function several times...

For the first part, you may want to look into changing your html structure so the js file is only included once (even though js files are cached by the browser, and the second time may not actually go to the server -- depending of several factors... there's still a penalty)

Now as for declaring your function only once, remember that functions are also object (1st class citizens) in js, so you can test if a function is already define as if you were testing an object.... if(!window.myFunc) { window.myFunc = function(){} }...

You may want to look a bit into functions and scoping in js.. here are some links

http://robertnyman.com/2008/10/09/explaining-javascript-scope-and-closures/

http://www.yuiblog.com/blog/2010/02/24/video-crockonjs-3/

http://www.slideshare.net/douglascrockford/crockford-on-javascript-act-iii-function-the-ultimate

Comments

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.