Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Sort HTML attributes with JavaScript

How would I sort HTML attributes using JavaScript?

I have this HTML:

<table>
    <tbody>
        <tr>
            <td>Cell 0,0</td>
            <td>Cell 1,0</td>
            <td>Cell 2,0</td>
        </tr>
        <tr>
            <td>Cell 0,1</td>
            <td rowspan="2" colspan="2">Cell 1,1
                <br>Cell 2,1
                <br>Cell 1,2
                <br>Cell 2,2</td>
        </tr>
        <tr>
            <td>Cell 0,2</td>
        </tr>
    </tbody>
</table>

And I want to sort all attribute in all elements into alphabetical order. E.g:

<td colspan="2" rowspan="2">Cell 1,1

The sort function could either be based on a HTML string, or a jQuery object, or a node (it doesn't matter which one).

The reason I need this is because I am doing a diff (with JS, in the browser, after a failed unit test) between 2 sets of HTML and the attribute order is making it fail.

So my questions are:

How can I reorder a nodes attributes?, Or how can I reorder attributes in an HTML string?, Or how can I reorder a jQuery elements attributes?

I haven't got any code for it yet, as I am unsure which method would be the best.

like image 920
Petah Avatar asked Dec 06 '12 21:12

Petah


1 Answers

Have no idea why you need do this with javascript, but it was rather interested. Okay, according spec:

Objects implementing the NamedNodeMap interface are used to represent collections of nodes that can be accessed by name. Note that NamedNodeMap does not inherit from NodeList; NamedNodeMaps are not maintained in any particular order. Objects contained in an object implementing NamedNodeMap may also be accessed by an ordinal index, but this is simply to allow convenient enumeration of the contents of a NamedNodeMap, and does not imply that the DOM specifies an order to these Nodes.

So you could order by changing numeral index, after a while there is my attempt which works smooth in Chrome.

(function(){
  var xpath = '//table/tbody/tr[2]/td[2]',
      attrs = document.evaluate(xpath, document, null, XPathResult.ANY_TYPE, null),
      serializer = new XMLSerializer(),

      el = attrs.iterateNext(),
      act = el.attributes,

      i = act.length,
      _l = i,
      _nodeArr = [],
      _nodeArrKeys = [],
      name;

  console.log(serializer.serializeToString(el));

  for (i ;i--;) {
    name = act[i].nodeName;
    _nodeArr[name] = (act.removeNamedItem(name));
    _nodeArrKeys[i] = name;
  }

  _nodeArrKeys = _nodeArrKeys.sort();
  i++;

  for (i;_l>i;i++) {
    act.setNamedItem(_nodeArr[_nodeArrKeys[i]]);
  }

  console.log(serializer.serializeToString(el));
})();

console log output

<td zataa="123" bbbrowspan="2" cccattr="val" aaacolspan="2">Cell 1,1
                    <br>Cell 2,1
                    <br>Cell 1,2
                    <br>Cell 2,2</td>

<td aaacolspan="2" bbbrowspan="2" cccattr="val" zataa="123">Cell 1,1
                    <br>Cell 2,1
                    <br>Cell 1,2
                    <br>Cell 2,2</td> 
like image 185
dmi3y Avatar answered Sep 19 '22 06:09

dmi3y