// ==UserScript==
// @name           Trac: Hide svn props changes
// @namespace      http://djce.org.uk/greasemonkey
// @description    In Trac changesets, show/hide props (mainly svn:mergeinfo)
// @include        http://devtools.ips.radio.bbc.co.uk/ips_toolkit/changeset*
// @include        http://*/trac/changeset*
// ==/UserScript==

try {
	// Simply adds a class to mergeinfo things.  Your style sheet can then
	// suppress these if you wish.
	var hide_element = function(e) {
		var c = e.getAttribute("class");
		if (!c) c = "";
		c = c+" " + "svnmergeinfo";
		e.setAttribute("class", c);
	};

	var find_mergeinfo_deltas = function() {
		var x = document.evaluate(
			'//ul[@class="props"]/li/strong',
		       document, null, XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE, null
		);

		var r = [];

		for (var i=0; i<x.snapshotLength; ++i)
		{
			var e = x.snapshotItem(i);

			var v = e.firstChild.nodeValue;
			if (!v || !v.match(/^\s*svn:mergeinfo\s*$/))
				continue;

			r[r.length] = e;
		}

		return r;
	};

	var count_child_by_tag = function(p, tag) {
		var n = 0;
		for (var c = p.firstChild; c ; c = c.nextSibling) {
			if (c.nodeName == tag) ++n;
		}
		return n;
	};

	var first_child_by_tag = function(p, tag) {
		var n = 0;
		for (var c = p.firstChild; c ; c = c.nextSibling) {
			if (c.nodeName == tag) return c;
		}
		return null;
	};

	var hide_file_entry = function(id) {
		var x = document.evaluate(
			'//dd[@class="files"]/ul/li[./a/@href="#' + id + '"]',
		       document, null, XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE, null
		);

 		if (x.snapshotLength == 1)
 		{
			hide_element(x.snapshotItem(0));
		}
	};

	// li.entry > ul.props > li > strong
	var hide_one_svnmergeinfo = function(mergeinfo_li) {
		hide_element(mergeinfo_li);

		var ul_props = mergeinfo_li.parentNode;
		if (count_child_by_tag(ul_props, "LI") == 1) {
			hide_element(ul_props);

			// If no content diffs, hide the whole file
			var li_entry = ul_props.parentNode;
			if (count_child_by_tag(li_entry, "TABLE") == 0) {
				hide_element(li_entry);
				// Hide the file's entry in dd.files > ul

				var h2 = first_child_by_tag(li_entry, "H2");
				if (h2) {
					var id = h2.getAttribute("id");
					hide_file_entry(id);
				}
			}
		}
	};

	/*

	   A single file's detail entry:

	<li class="entry">
        <h2 id="file2"><span class="switch"/>
          <a href="/trac/changeset/18228/wfe/branches/232-Pub-v2-Asset-Workflow/t/utils/mp_yaml.t" title="Show the changeset 18228 restricted to wfe/branches/232-Pub-v2-Asset-Workflow/t/utils/mp_yaml.t">wfe/branches/232-Pub-v2-Asset-Workflow/t/utils/mp_yaml.t</a>
        <a class="anchor" href="#file2" title="Link to this diff"> ¶</a></h2>
        <ul class="props">
            <li>Property <strong>svn:mergeinfo</strong><div class="diff">
  <ul class="entries">
      <li class="entry">
        <h2><span class="switch"><span class="active">Tabular</span><span>Unified</span></span>
           
        </h2>
        <table cellspacing="0" summary="Differences" class="inline">
	  ...
        </table><pre style="display: none;"/>
      </li>
  </ul>
</div></li>
        </ul>
      </li>

      */

	var hide_all_svnmergeinfo = function() {
		var r = find_mergeinfo_deltas();
		for (var i=0; i<r.length; ++i)
			hide_one_svnmergeinfo(r[i].parentNode);
	};

	hide_all_svnmergeinfo();

} catch(e) {
	alert("Error in trac_hide_svn_props_chan.user.js: " + e);
}

