IE7: How do I create a real NodeList?

1.2k views Asked by At

I'm trying to make my current project IE7-compatible. We are not using jQuery, but instead using querySelectorAll for our selector needs. However, IE7 doesn't support querySelectorAll, so I've monkey-patched it with code from https://gist.github.com/868532. It actually works fine, except for one small difference: instead of a NodeList like the original querySelectorAll, it returns an array. Since I'd like to stay as compatible as possible, I wanted to make that function return a NodeList. Using some method found on the net, I've adapted the gist to this:

(function(d) {
     d=document, a = d.styleSheets[0] || d.createStyleSheet();

     if (! vxJS.isHostMethod(d, 'querySelectorAll')) {
         d.querySelectorAll = function(e) {
             a.addRule(e,'f:b');

             for (var l=d.all, b=0, c=d.createDocumentFragment(),f=l.length; b<f; b++) {
                  l[b] && l[b].currentStyle.f && c.appendChild(l[b].cloneNode(true));
             }
             a.removeRule(a.rules.length - 1);
             return c.childNodes;
         };
     }
 })();

My problem with this code is that appendChild removes a node from its original location in DOM tree, therefore I tried creating a clone with cloneNode, which obviously creates valid node clones, which are not the original nodes and thus cannot be used in further code.

Is there any way I can put a real node reference into a NodeList?

2

There are 2 answers

2
Šime Vidas On

I don't think that it can be done.

The NodeList instances which IE7 is able to produce are live NodeLists. However, the querySelectorAll method is defined to return a static NodeList instance. I don't believe that IE7 knows what a static NodeList is - those were (afaik) only introduced in the Selectors API.

Read about live NodeLists and static NodeLists here.

0
Cabu On

Perhaps you can make your Array mimicking NodeList by adding the item() method.

if (!Array.prototype.item) {
    Array.prototype.item = function (i) {
        "use strict";

        return this[i];
    };
}