Search code examples
javascriptconstructormoduledesign-patternsprivate

Module pattern with constructor


I' ve tried combining the module pattern with a constructor function but it seems I' m looking over something. After instantiating two objects and showing their properties both instance var' s seem to reference the same object.

This is a small example I put together.

<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=utf-8">     
        <title>test</title>

        <script type="text/javascript">
            var guidUtils = {
                /* Generates a simple UUID/GUID based on some randomisation.
                 *
                 */
                guidGenerator:function () {
                    var S4 = function () {
                        return (((1 + Math.random()) * 0x10000) | 0).toString(16).substring(1);
                    };
                    return (S4() + S4() + "-" + S4() + "-" + S4() + "-" + S4() + "-" + S4() + S4() + S4());
                }
            };


            var Car = (function () {

                // private variables and functions
                var thiz;
                var ID = 'bar';
                var model;

                var setID = function(id){
                    ID = id;
                };

                var getID = function(){
                    return ID;
                };

                var  setModel = function(pModel){
                    model = pModel;
                };

                var  getModel = function(){
                    return model;
                };

                // constructor
                var Car = function (pModel) {
                    thiz=this;
                    ID = guidUtils.guidGenerator();
                    model = pModel;
                    init();
                };

                //intialisation
                function init(){

                }

                // prototype
                Car.prototype = {
                    constructor: Car,
                    getID: getID,
                    getModel: getModel

                };

                // return Car
                return Car;
            })();

            function show() {
                var car1 = new Car("audi");
                var car2 = new Car("BMW");
                var car1div = document.getElementById("car1");
                var car2div = document.getElementById("car2");
                car1div.innerHTML=car1.getID()+" is a "+car1.getModel();
                car2div.innerHTML=car2.getID()+" is a "+car2.getModel();
            }

        </script>       
    </head
    <body>
        <a onclick="show()" href="javascript:void(0);">show</a>
        <div id="car1"></div>
        <div id="car2"></div>
    </body>
</html>

The result is:

screenshot of result

Could some explain where exactly I' m making the wrong assumptions?


Solution

  •  var thiz;
     etc... 
        // constructor
        var Car = function (pModel) {
            thiz=this;
            etc...
    

    is the problem. This creates a kind of static variable, shared by all instances of the class. All instance methods and properties have to be bound to the prototype and this. Eg:

        var Car = function (pModel) {
            this.ID = guidUtils.guidGenerator();
            this.model = pModel;
            this.init();
        };
    
        // Removed: "var setID = " Instead, bind it to the prototype:
        Car.prototype.setId = function(id){
            this.ID = id;
        };
    

    See also: