svp
svp

Reputation: 495

Controller inheritance in Angularjs: couldnot call the child methods from html

I am trying to achieve Controller inheritance in Angularjs and followed several articles and examples and couldnot make it work.

I have common functionality across 2 controllers and i have created BaseController for common functionalities and ChildControllers extended this controller.

HTMl file

 <div ng-controller="ChildCtrl1"> 
  <div>Gettting absolute url from parent: <strong>{{commonVar}}</strong></div>
  <button  class="btn btn-primary pull-left" ng-click="scopeChildMethod1 ()">OK</button>
</div>

BaseCtrl.js

var dependencies = []; 
define( dependencies, function()
{   
  function BaseCtrl($scope,$location) {
        $scope.commonVar = 42;
        $scope.commonMethod1 = function () {
            alert('test');
          };
  };
    BaseCtrl.prototype.commonMethod2 = function () {
      alert('test2');
    };

  return BaseCtrl;

 });

ChidlCtrl1.js

var dependencies = [ './module','./BaseCtrl'];
define(dependencies, function (module,BaseCtrl) {
  return module.controller('ChildCtrl1', function ($scope,$location){
    var  ChildCtrl1=function($scope, $location) {
        BaseCtrl.call(this, $scope, $location);
        $scope.scopeChildMethod1 = function () {
            alert('test');
          };

   }
      ChildCtrl1.prototype = new BaseCtrl($scope, $location);

      ChildCtrl1.prototype.childMethod2 = function () {
        alert('test');
      };

     return ChildCtrl1;
});

 });

I see that child scope method is not triggered on button click??where as i can trigger the scope method in BaseController.I am not sure whats wrong in the above code as in why i cannot trigger child methods???

Any help will be appreciated.

Upvotes: 0

Views: 210

Answers (1)

Esteban Felix
Esteban Felix

Reputation: 1561

module.controller takes in a function for the controller as the second argument. You just need to change how you're calling module.controller, like so:

var ChildCtrl1 = function ($scope, $location) {
    BaseCtrl.call(this, $scope, $location);
    $scope.scopeChildMethod1 = function () {
        alert('test');
    };
    $scope.childMethod2 = ChildCtrl.childMethod2;

};

ChildCtrl1.prototype =  Object.create(BaseCtrl.prototype);

ChildCtrl1.prototype.childMethod2 = function () {
    alert('test');
};


module.controller('ChildCtrl1', ChildCtrl1);

Note however that this line:

ChildCtrl1.prototype = new BaseCtrl($scope, $location);

was changed to this:

ChildCtrl1.prototype = Object.create(BaseCtrl.prototype);

Unfortunately the original line won't work as $scope and $location don't exist at this point, but it's fine as you're calling BaseCtrl.call(this, $scope, $location); in the ChildCtrl constructor anyway.

IE8

If you need this to work in IE8, you can add a polyfill:

if (typeof Object.create != 'function') {
  Object.create = (function() {
    var Object = function() {};
    return function (prototype) {
      if (arguments.length > 1) {
        throw Error('Second argument not supported');
      }
      if (typeof prototype != 'object') {
        throw TypeError('Argument must be an object');
      }
      Object.prototype = prototype;
      var result = new Object();
      Object.prototype = null;
      return result;
    };
  })();
}

Upvotes: 3

Related Questions