John Resig wrote:
Filtering NodeLists/StaticNodeLists, Queries on NodeLists/StaticNodeLists:
Neither of these are useful, as is, to libraries.

I believe this would be handled using the Array.filter() method, with a
callback that checks if the selector matches the element, as Jonas pointed
out:

  filteredArray = myArrayOfNodes.filter(function(node) { return
node.matchesSelector("some>selector"); });

(That could also work with the above Selector.matches() proposal)


Array.filter() will meet the need of filtering
NodeLists/StaticNodeLists/Arrays of Elements - sure - but it won't meet the
need of NodeList.querySelectorAll (especially if that works with an
array-like collection of DOM elements).

Right, but I'm dealing with that as an entirely separate issue, which I disucssed later on in that email.

Basic filtering of nodelists is bug 5864, which I've resolved WONTFIX for now because the functionality doesn't seem too desirable or beneficial.

http://www.w3.org/Bugs/Public/show_bug.cgi?id=5864

The issue you're discussing is bug 7707, which is still open.

http://www.w3.org/Bugs/Public/show_bug.cgi?id=7707

The problem is that when you have multiple collections of DOM elements and
you wish to reduce them to a single collection it ends up being a very
expensive task. The steps are as follows:
   - The collections must be merged together into a single array of DOM
elements.
   - The elements must be sorted to be in document order.
   - Duplicate elements must be removed from the collection.

So the question is, at which point in the chain do you want to address this issue? The options are:

A) Have specific selectors API feauture that allowed executing a
   selector query on a whole collection of elements that returns a
   single, sorted collection of unique elements.

B) A more generic API for being able to easily merge and sort
   NodeLists/Arrays of elements.

Option A saves the step of having to run the queries on each individual element manually and just returns a merged and sorted collection of unique elements. But it's limited to running selector queries, rather than any other getElementsBy*() method to obtain the results.

Option B is more generic in that it could potentially merge and sort any set of NodeLists, and those NodeLists could be obtained by any method, but would still require running the queries on each element individually to obtain the the lists that then need to be merged.

Both options present an issue with sorting, since they could result in lists that contain both connected and disconnected elements, and the sort order for connected elements in relation to disconnected elements would need to be defined.

Option B seems potentially harder to define and possibly implement, especially if you want to be able to sort merge NodeList objects with Array objects. Since Arrays aren't limited to just containing DOM Nodes, the issue of what to do with other types objects and how to sort them along with the Nodes is complicated.

It would be great to have a separate, standalone, function that handles
these merge/sort/unique operations for collections of DOM elements
(especially if they're disconnected from the document!).

The proposal from my previous mail falls into Option A. Would it address this issue adequately? Specifically, defining document.createSelector() and a Selector interface that allows running a query like this:

var elements = [...] // Some Array (or NodeList) of Elements
var selector = document.createSelector("em, strong");
var list = selector.querySelectorAll(elements);

This is equivalent to iterating over the elements array, running elements[i].querySelectorAll("em, strong") on each, and then merging/sorting all of the results into a single collection.

If there was a merge/sort/unique method it would drop the need for having a
NodeList/Array.querySelectorAll.

Whether we should go for the extra complexity required for this really depends on the use case you're trying to address. Do you just need to merge NodeLists that are all obtained via querySelector methods, or do you need to merge any random NodeLists or Arrays that could be obtained via querySelector*() or getElementsBy*(), or wherever else.

--
Lachlan Hunt - Opera Software
http://lachy.id.au/
http://www.opera.com/

Reply via email to