Search code examples
javascriptfunctioncallprototyperadix

JavaScript: Call base function from prototyped inheritance


var super_class = function(p) {
    this.p = p + 1;
    this.method = function(a, b) {
        // some code
    };
};

var base_class = function(o) {
    this.o = o;
    super_class.call(this, o);
    this.method = function(a, b) {
        // call super_class .method();
        // some code
    }
}

base_class.prototype = new super_class();

var bc = new base_class(0);
var v1 = bc.o; // 0
var v2 = bc.p; // 1

How can I call the super_class method when the name and properties are supposed to be identical. If I changed the name, I would just call this.method(3, 4); from within another function. I'm creating an extension class to another extension class, so changing the name of the function will not help me.

Also, storing the function in a private variable var pmethod = this.method; is sloppy at best.


Solution

  • Your current implementation has an error at super_class(this, o);. Either replace it with super_class.call(this, o), or correctly implement an initializer method:

    // Basic super class method.
    var Super_class = function(p) {
        this.init(p); // Call initializer
    };
    
    // Define prototype properties and methods
    Super_class.prototype = {
        constructor: Super_class,
        init: function(p) { this.p = p + 1; },
        method: function(a, b) {
            console.log("Super class method, arguments: " + [a,b]);
        }
    };
    
    // Define base_class
    var Base_class = function(o) {
        this.o = o;   // Initialize `o` property
        this.init(o); // Initialize p variable through the initializer
    };
    // Extend `Base_class` prototype with `method`.
    Base_class.prototype.method = function(a, b) {
        // Call the method from the parent = Super_class.prototype.method
        this.constructor.prototype.method(a, b);
    };
    
    Base_class.prototype = new Super_class; // Set prototype to `super_class`.
    
    var bc = new Base_class(0);
    var v1 = bc.o; // 0
    var v2 = bc.p; // 1
    bc.method('Hi: ', [v1, v2]); // Prints "Super class method, arguments: Hi [0,1]"
    

    Alternatively, you can also push all methods of Base_class in Base_class itself and/or create a reference to the parent class:

    // Define base_class
    var Base_class = function(o) {
        var __super__ = this.constructor.prototype;
        this.o = o;   // Initialize `o` property
        this.init(o); // Initialize p variable through the initializer
        Base_class.prototype.method = function(a, b) {
            // Call the method from the parent = Super_class.prototype.method
            __super__.method(a, b);
        };
    };