Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Add function to object

I have the following code

var PROMO = PROMO || {};

PROMO.Base = (function () {
  var _self = this;

  var Init = function () {
    WireEvents();
  };

  var WireEvents = function () {
   //wire up events
  };

} ());

In the same file I have the code to call the above function

I am trying to get to an end point where I can use the following code

 $(document).ready(function () {
    PROMO.Base.Init();
 });

this gives the error

Cannot call method 'Init' of undefined

Now I know there are many ways to write javascript, but in this case I want to be able to call my functions, or least the Init method in the way shown above.

like image 526
dan_vitch Avatar asked May 07 '13 19:05

dan_vitch


2 Answers

var PROMO = PROMO || {};

PROMO.Base = (function () {
  var _self = this;

  var Init = function () {
    WireEvents();
  };

  var WireEvents = function () {
   //wire up events
  };

  var reveal = {
        Init: Init        
  };

  return reveal;

} ());

You need to return the public facing functions. See updated code.

like image 93
Drew Avatar answered Sep 29 '22 08:09

Drew


Working fiddle with both patterns, using IIFE and direct attribution.

Using var makes the definition private and your function is returning nothing. Use this:

PROMO.Base = {
    Init: function() {
    },
    WireEvents: function() {
    };
};

You are wrapping the definition with an IIFE(Immediately Executed Function Expression). So your PROMO.Base object will be assigned the value of that (function(){//blabla})(); returns. But your function doesn't have a return statement. By default it will return undefined.

Which is way your PROMO.Base will be undefined and you get this:

Cannot call method 'Init' of undefined

If you really want that IIFE:

var PROMO = PROMO || {};
// NEVER use _self = this inside static functions, it's very dangerous.
// Can also be very misleading, since the this object doesn't point to the same reference.
// It can be easily changed with Function.prototype.call and Function.prototype.apply
PROMO.Base = (function () {

    _PROMO = {
        Init : function () {
            document.body.innerHTML += "itworks";
        },
        WireEvents : function () {
   //wire up events
        }
    }
    return _PROMO;
} ());
PROMO.Base.Init();

Update

The better and easier pattern is to simply assign the functions to PROMO.Base. Dully note you should not capitalize static functions, but only constructors. So if something is not meant to be instantiated, don't call it Init, it should be init. That is the convention.

var PROMO = {};
PROMO.Base = {};
PROMO.Base.init = function() {
    console.log("this works");
};
PROMO.Base.wireEvents = function() {
    console.log("this is a static function too");
};
like image 44
flavian Avatar answered Sep 29 '22 08:09

flavian