3

When I run my code below then it shows error object is not a function in console. This error is on this line var todo = new Todo('contents'); in my script.js file. How can I make it work?

Here is my todo.js file

var Todo = (function(c) {
var contents = $('.' + c);

var showel = function (d) {
    contents.prepend(d);
},

add = function (name) {
    if(name != "") {
        var div = $('<div class="names"></div>')
        .append('<span>' + name + '</span>')
        .append("<button class='update' class='update'>Edit</button>")
        .append("<button class='remove' name='remove'>Remove</button>");
    }

    return showel(div);
},

addUpdateField = function (dom) {
    var name = dom.parent().find('span').text(),
        field = $('<input type="text" value="' + name + '" />'),
        update = $('<button class="updateBtn">Update</button>');
    dom.parent().html('').append(field).append(update);

    return;
},

update = function(el) {
    var val = el.parent().find('input').val();
    el.parent().html('<span>' + val + '</span>')
    .append('<button class="update" class="update">Edit</button>')
    .append('<button class="remove" class="remove">Remove</button>');

    return;
},

remove = function (el) {
    return el.remove();
};

return {
    add             : add,
    update          : update,
    remove          : remove,
    addUpdateField  : addUpdateField
};
})();

here is my script.js file

$(function () {
var todo = new Todo('contents');

$('.addBtn').on('click', function() {
    var name = $(this).parent().find('input[type="text"]').val();
    todo.add(name);
});

$('.contents').on('click', '.remove', function() {
    var el = $(this).parent();
    todo.remove(el);
});

$('.contents').on('click', '.update', function() {
    var dom = $(this);
    todo.addUpdateField(dom);
});

$('.contents').on('click', '.updateBtn', function() {
    var el = $(this);
    todo.update(el);
});

});

here is html code

<html>
<head>
<script type="text/javascript" src="http://code.jquery.com/jquery-latest.js">    </script>
<script type="text/javascript" src="todo.js"></script>
<script type="text/javascript" src="script.js"></script>
<link rel="stylesheet" type="text/css" href="styles.css">
<title></title>
</head>

<body>
<div class="container">
    <label>Name</label>
    <input type="text" class="name" name="name" />
    <input type="button" class="addBtn" name="add" value="Add" />
    <div class="contents"></div>
</div>
</body>
</html>
1
  • I think you should change the ASEF to a normal function Commented Aug 14, 2012 at 11:48

1 Answer 1

9

You are immediately executing the function that is assigned to Todo. That function returns an object, so Todo refers to the returned object, not a function (hence the "Not a function" error).

I assume you intended something along the lines of this:

var Todo = function () {

    this.add = function () { //Note the use of `this` here
        //Do stuff
    };
    //etc...

}; //No self-invoking parentheses here

Now, Todo refers to a constructor function which you can invoke with the new operator, as you are currently trying to do.

Also note that this pattern will result in every instance of Todo having a separate copy of each method, which isn't very efficient. It would be better to declare the methods as properties of the prototype:

var Todo = function () {
    //Initialize the Todo instance
};
Todo.prototype.add = function () {
    //Do stuff
};

Now, all instance of Todo will share a single copy of the methods.

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

4 Comments

It works like this. But I wanted to modify my code so that it should work the way I am trying to do in my example above. How can I modify my code so that it works.
I don't get what you are trying to achieve... what's wrong with changing it to be like this?
That article is describing how to namespace functions... it's not describing constructor functions, which is what you need here. The examples in that article would not be called with new. Also, maybe you should heed the warning at the top of the article... "This article is obsolete".

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.