errorreplicating
errorreplicating

Reputation: 611

JavaScript throws TypeError saying that my variable is undefined

I don't have much experience in JavaScript, so far I have this:

  function loop() {
    var authorDivs = document.getElementById('ctl00_MainContent_MCPObjectInfo_dvCreatorView').getElementsByTagName("div");

    for (var i = 0; i < authorDivs.length; i++) {
        var divOfDiv = authorDivs[i].getElementsByTagName("div");

        if (typeof divOfDiv.item(i) === 'undefined' || divOfDiv.item(i) === null) {
            console.log("This is undefined or null");
        }
        else {
            var realDivs = divOfDiv.item(i);
            realDivs.item(i).textContent = "please work plz";
        }
    }
}

I get the following error from the console in FireFox: TypeError: realDivs is undefined on this line: realDivs.item(i).innerHTML = "please work plz";

Essentially what I have (in my mind) is a loop that goes through authorDivs and gets all of the divs within those divs and saves them in divOfDiv. I then check to see if the divs in divOfDiv are undefined or null, if they are not then those divs get saved in a variable realDivs which I then use to edit the innerHTML. That's what I'd ideally like to see happen, what is causing the error? What am I doing wrong?

Note: I do not have access to jQuery but only JavaScript.

Edit: I've added the changes suggested below and its fixed that -- thanks! But I'm now getting the following error: TypeError: realDivs.item is not a function

What is causing that? And on another note how do I know when I'm dealing with an array and when I'm dealing with an HTMLCollection? Do you just assume? I've never used a loosely typed language before so its new to me.

Upvotes: 0

Views: 17264

Answers (3)

Srini
Srini

Reputation: 348

There are two problems in the code.

  1. comparing DOM object with 'undefined' and null. If div tag is not available in authorDivs[i], it will return empty DOM array. So, comparision of empty DOM array with undefined and null is not good approach. We can use array length property for doing validation.

    divOfDiv = authorDivs[i].getElementsByTagName("div");
    if(divOfDiv.length > 0) { console statement}

  2. As item(i) is already return single DOM element, item(i) of "realDivs" variable is not proper approach. In addition to this, innerHTML method needs to be used after validating whether realDivs contains DOM element. Please update the code as below.

    var realDivs = divOfDiv.item(i); realDivs ? (realDivs.innerHTML = "please work plz"): null;

Note : item(i) will return null if DOM is not available.

Upvotes: 0

Bergi
Bergi

Reputation: 664513

Well, you'll need to move that code inside the conditional block that is supposed to prevent it! Also, || "null" is not going to work as you expect, you'll need to check for || divOfDiv.item(i) === null explicitly.

So try

for (var i = 0; i < authorDivs.length; i++) {
    var divOfDiv = authorDivs[i].getElementsByTagName("div");

    if (divOfDiv.item(i) == null) {
        console.log("This is undefined or null");
    } else {
        var realDivs = divOfDiv.item(i)
        realDivs.item(i).innerHTML = "please work plz";
        console.log(divOfDiv.item(i));
    }
}

However, that still doesn't really work for two reasons:

  • The i index you use to access the i-th divOfDiv comes from the iteration over authorDivs - hardly what you want. Instead, use a second loop over all divOfDivs.
  • Your realDivs variable does hold a single <div>, which does not have an .item method. You'd just directly access its .innerHTML property.

So you should use

var authorDivs = document.getElementById('authorView').getElementsByTagName("div");
for (var i=0; i<authorDivs.length; i++) {
    var divsOfDiv = authorDivs.item(i).getElementsByTagName("div");

    for (var j=0; j<divsOfDiv.length; j++) {
        var realDiv = divsOfDiv.item(j);
        realDiv.innerHTML = "please work plz";
        console.log(realDiv);
    }
}

Upvotes: 2

djaszczurowski
djaszczurowski

Reputation: 4515

it will happen in case when your if (typeof divOfDiv.item(i) === 'undefined' || 'null') returns true. Then you never initialize realDivs (what would happen if condition was falsy). Later you try to call item function on that unitialized object

Upvotes: 2

Related Questions