11

I like to organize my javascript in namespace style like below. What I want to know : is there another (shorter?) way to call myFirstFunction() from mySecondFunction()? I tried this.myFirstFunction() and it's not working so maybe there's some kind of mysterious trick here that I don't know.

var myNameSpace = {
    myFirstFunction: function(){
        alert("Hello World!");
    },
    mySecondFunction: function(){
        myNameSpace.myFirstFunction();
    }
}

Thanks for your help as usual, people of SO! :)

1
  • Your example is correct, it should work. Commented Nov 3, 2010 at 2:34

5 Answers 5

13

As written in your example code, this.myFirstFunction() would work. Your code is likely simplified to illustrate your problem, so it would probably help to see the actual code to tell why it doesn't work with this.

One possible reason that it fails would be if the code where you call this.myFirstFunction() is inside a closure. If so, this would be a reference to the closing function, not your namespace and would therefore fail. See here for a contrived example based on your code to see what I mean. Again, having a look at the actual code would probably be helpful to diagnose what's going on.

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

2 Comments

Good simple answer. I understood everything with your jsfiddle example. Thanks, you just made my js code a little bit more clean! And you were right, I simplified my code to post it here, and my call to the function was in a closure. I didn't know that it would affect the "this" keyword. Thanks again!
No problem, Gabriel. Glad it helped. :)
2

Your suggestion to use 'this' should work. i.e.:

var myNameSpace = {
    myFirstFunction: function(){
        alert("Hello World!");
    },
    mySecondFunction: function(){
        this.myFirstFunction();
    }
}

Result:

myNameSpace.mySecondFunction() // "Hello World!".

Comments

2

If you want it to be shorter maybe you should consider the following pattern:

Javascript Design Pattern Suggestion

basically for your example:

var myNameSpace = (function()
{
    function _myFirstFunction(){
        alert("Hello World!");
    }

    function _mySecondFunction(){
        _myFirstFunction();
    }

    return {
        MyFirstFunction : _myFirstFunction,    
        MySecondFunction : _mySecondFunction
    };
})();

I find this to be the cleanest pattern, also providing "private/public" variables in javascript that's otherwise pretty much impossible

Comments

0

In some cases the this keyword should work fine. If you explicitly call myNameSpace.mySecondFunction() then this.myFirstFunction() will execute as intended.

If you are using myNameSpace.mySecondFunction as an event handler it likely will not. In the case of an event handler you would need some way to refer to the namespace you want to use. A lot of JavaScript frameworks provide a way to define what the this keyword refers to. For example, in MooTools you can do myNameSpace.mySecondFunction.bind(myNameSpace) which will cause this to refer to myNameSpace inside mySecondFunction. If you are not using a framework you could make your event handler an anonymous function like:

document.getElementById('myId').addEventListener('click', function(e) {
  myNameSpace.mySecondFunction.call(myNameSpace);
});

For more information on the call method I would refer to the MDC page for the call function or you could use apply which behaves similarly to call but passing an array of arguments for the second paramter rather than having a varargs like approach for additional parameters.

All of these suggestions are predicated on defining your namespace as @Harnish suggested:

var myNameSpace = {
  myFirstFunction: function(){
    alert("Hello World!");
  },
  mySecondFunction: function(){
    this.myFirstFunction();
  }
}

For more information about JavaScript function binding I'd highly suggest reading Justin's article on Function scope and binding in JavaScript

Comments

0

If you are attaching to event:

possible issue could be if you are attaching Namespace's function to event, like:

$(el).on("click", nameSpace.myFunc);

....

nameSpace = {

    myFunc: function(){
       this.anotherFunc();
    }

}

that will throw error.

Solution 1

You may change this.anotherFunc() with nameSpace.anotherFunc()

Solution 2

You might change

$(el).on("click", nameSpace.myFunc);
// to ----->
$(el).on("click", function(){ nameSpace.myFunc(); }  );

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.