0

I've been struggling with this bit of code for quite a few days. Essentially it's an object that takes the input of 3 text boxes and concatenates them into a string.. or that's what it should do.

Student.toString returns as undefined or "Uncaught TypeError: Property 'Student' of object [object Object] is not a function" when it should be last name, first name and then id number. Can anybody explain what I did wrong on this?

    <div id='textInside'>
    First Name:<input type='text' id='fName'><br>
    Last Name:<input type='text' id='lName'><br>
    Student Id: <input type='text' id='stuId'><br>
    <button onclick='readInputs()'>Update</button>

    <p id='stuInfo'></p>
</div>

<script type='text/javascript'>
    var fiName = document.getElementById('fName');
    var laName = document.getElementById('lName');
    var studeId = document.getElementById('stuId');
    var toP = document.getElementById('stuInfo');

    var Student = new Object;

    function Student() {
        this.firstName = fiName;
        this.lastName = laName;
        this.studentId = studeId;
        this.toString = function() {var result = toP.innerHTML = this.lastName + this.firstName + this.studentId};
            return result;
        this.readInputs = function() { };
    }



    function readInputs() {
        Student();
        Student.toString();
    }
</script>
anon146
  • 7
  • 1
  • 3
  • 2
    next time, put your example in a JSfiddle and you'll make us all that much happier. http://jsfiddle.net/YnqxC/ – erik258 Mar 20 '14 at 02:07
  • 2
    You have two `Student`. And you didn't use `new`, trouble. And your `toString` requires an instance. – elclanrs Mar 20 '14 at 02:09
  • There are several issues with the code you've posted. It might be best to clarify what you want to do. – Femi Mar 20 '14 at 02:11
  • @DanFarrell—no, it won't. Posting concise code here is to be preferred as it is more convenient and keeps the code associated with the question rather than abstracted to some other site. – RobG Mar 20 '14 at 02:42
  • The two aren't mutually exclusive. – erik258 Mar 20 '14 at 02:45
  • Maybe the following answer can help you understanding prototype and constructor functions: http://stackoverflow.com/a/16063711/1641941 It may be a lot to take in but it's worth it. – HMR Mar 20 '14 at 08:24

5 Answers5

3

There is… a lot wrong here.

var Student = new Object;

function Student() {
    this.firstName = fiName;
    this.lastName = laName;
    this.studentId = studeId;
    this.toString = function() {var result = toP.innerHTML = this.lastName + this.firstName + this.studentId};
        return result;
    this.readInputs = function() { };
}

First off, use {}, not new Object. Next, this will just set Student to a new Object and overwrite your function, since the function is hoisted. I’m pretty sure you just meant to have the one function there.

Next, return result; isn’t inside your toString function, which is an error, and again not the one you’re reporting. Is this actually your code? Use the prototype, too. And toString shouldn’t have side-effects and constructors shouldn’t read globals.

function Student(firstName, lastName, studentId) {
    this.firstName = firstName;
    this.lastName = lastName;
    this.studentId = studentId;
}

Student.prototype.readInputs = function() {};

Student.prototype.toString = function() {
    return this.lastName + this.firstName + this.studentId;
};

Now readInputs can look like this (does it have something to do with the empty function on Students, by the way?):

function readInputs() {
    var s = new Student(fiName.value, laName.value, studeId.value);
    toP.innerHTML = s.toString();
}

Note that you have to use new with constructors to create this properly, and grab the value property of input elements, and actually do something with the return value of the function.

This error:

Uncaught TypeError: Property 'Student' of object [object Object] is not a function

seems impossible to me, but I could just be missing something. (Are you on IE8?)

Ry-
  • 218,210
  • 55
  • 464
  • 476
  • Nice answer. The error is because of the hoisting, you mentioned it. A `new Object` is not a function, in `Student()`. – elclanrs Mar 20 '14 at 02:19
  • @elclanrs: Yep, I was just wondering where the “of [object Object]” is coming from. Some version of some browser, I guess. – Ry- Mar 20 '14 at 02:21
  • 2
    I see, yeah I'll go for IE, blaming on IE seems right. – elclanrs Mar 20 '14 at 02:23
  • @elclanrs—blame IE for what? The error is returning the `[[Class]]` of the object in much the same way *typeof* does and is saying "this object is class Object and doesn't implement call, therefore it isn't a function". I am no fanboi for IE, but there is no reason to bash it here. – RobG Mar 20 '14 at 03:41
  • @RobG: No, I just mean that the right error seems like it would be “TypeError: Student is not a function” or “TypeError: object is not a function”. It’s a variable, and it doesn’t really look like a property of `window` (which I’m assuming is how this error is treating it). Plus `[object Window]` would be useful there. – Ry- Mar 20 '14 at 19:36
0

Try changing this

 var student = new Student(fiName,laName,studeId);
 var res = student.toString();

 function Student(fiName,laName,studeId) {
        this.firstName = fiName;
        this.lastName = laName;
        this.studentId = studeId;
    }

   Student.prototype.toString = function() {
        return this.lastName + this.firstName + this.studentId
    }

Above is an example of object oriented java script code. I have defined a Student constructor function and defined a toString method on the new Student type. It's recommended to add your methods to the prototype chain in order to tie them to the type and not just a particular instance.

TGH
  • 38,769
  • 12
  • 102
  • 135
0
<div id='textInside'>
First Name:<input type='text' id='fName'><br>
Last Name:<input type='text' id='lName'><br>
Student Id: <input type='text' id='stuId'><br>
<button onclick='readInputs()'>Update</button>

<p id='stuInfo'></p>
</div>

<script type='text/javascript'>
    var fiName = document.getElementById('fName');
    var laName = document.getElementById('lName');
    var studeId = document.getElementById('stuId');
    // Where is <node id="stuInfo" /> defined?..
    var toP = document.getElementById('stuInfo');

    function Student() {
        this.firstName = fiName.value;
        this.lastName = laName.value;
        this.studentId = studeId.value;
        this.toString = function() {
            var result = toP.innerHTML + this.lastName 
                + this.firstName + this.studentId
            return result;
            };
    }

    function readInputs() {
        var a_student = new Student();
        alert(a_student.toString());
    }
</script>
Femi
  • 1,332
  • 9
  • 20
0

You should put .value after you get the elements id. Because you can get the id of an element but not its value.

var fiName = document.getElementById('fName').value;

so that's makes your variable have a value.

nami
  • 1
-3

To instanciate on object you have to use the word new

Since you generate student, you have to give as argument to the constructor

The code should looke like this

<div id='textInside'>
    First Name:<input type='text' id='fName'><br>
    Last Name:<input type='text' id='lName'><br>
    Student Id: <input type='text' id='stuId'><br>
    <button onclick='readInputs()'>Update</button>

    <p id='stuInfo'></p>
</div>

<script type='text/javascript'>
var Student = function( option ) {
    this.firstName = option.fiName;
    this.lastName = option.laName;
    this.studentId = option.studeId;
    this.top = option.top;
};

Student.prototype.toString = function(){
     return document.write(this.lastName +" "+ this.fastName +" "+ this.studentId);
};

function readInputs() {
    var student = new Student({
         fiName: document.getElementById('fName').value.trim(),
         laName: document.getElementById('lName').value.trim(),
         studeId: document.getElementById('stuId').value.trim(),
         top: document.getElementById('stuInfo').value.trim()
    });
    student.toString();
}
</script>

Dimitri
  • 304
  • 3
  • 16