Difference between revisions of "MediaWiki:Common.js"

From Observer GigaFlow Support | VIAVI Solutions Inc.
Jump to: navigation, search
 
(2 intermediate revisions by one user not shown)
Line 1: Line 1:
GAMES
+
/* Any JavaScript here will be loaded for all users on every page load. */
MOVIES
+
TV
+
(function ($, mw, store) {
VIDEO
+
    "use strict";
WIKIS
+
    var articles;
Search
+
 +
    if (store && store.getItem('commonjs')) {
 +
        console.log('You have chosen to disable site-wide JavaScript ' +
 +
                    'in MediaWiki:Common.js. Please remove \'commonjs\' ' +
 +
                    'from localStorage to re-enable site-wide JavaScript.');
 +
        return;
 +
    }
 +
 +
    window.UserTagsJS = {
 +
modules: {},
 +
tags: {
 +
          heroicuser:  { u:'Most Heroic Contributor' },
 +
          imageeditor: { u:'Image Editor' },
 +
          retired: { u:'Retired Clasher' },
 +
        }
 +
    };
 +
    UserTagsJS.modules.custom        = {};
 +
    UserTagsJS.modules.inactive      = 30;
 +
    UserTagsJS.modules.newuser      = true;
 +
    UserTagsJS.modules.autoconfirmed = true;
 +
 +
    UserTagsJS.modules.mwGroups = [
 +
        'bureaucrat',
 +
        'sysop',
 +
        'chatmoderator',
 +
        'threadmoderator',
 +
        'rollback',
 +
        'patroller',
 +
        'bannedfromchat',
 +
        'bot',
 +
        'bot-global',
 +
    ];
  
START A WIKI
+
    UserTagsJS.modules.metafilter = {
Clash of Clans Wiki Editing MediaWiki:Common.js/AttackStrategies.js Need help editing?Notifications
+
        bureaucrat:     ['founder'],
You do not have permission to edit this page, for the following reasons:
+
        sysop:          ['founder', 'bureaucrat'],
 +
        chatmoderator:  ['founder', 'bureaucrat', 'sysop'],
 +
        threadmoderator: ['founder', 'bureaucrat', 'sysop', 'chatmoderator'],
 +
        imageeditor:    ['founder', 'bureaucrat', 'sysop', 'chatmoderator', 'threadmoderator'],
 +
        rollback:        ['founder', 'bureaucrat', 'sysop', 'chatmoderator', 'threadmoderator',
 +
                          'imageeditor'],
 +
    };
 +
 +
    UserTagsJS.modules.custom = {
 +
        'FaceBound': ['imageeditor'], // Image Editor
 +
    };
  
You are not allowed to execute the action you have requested.
+
    if (typeof(window.SpoilerAlert) === 'undefined') {
This page provides interface text for the software, and is protected to prevent abuse.
+
        window.SpoilerAlert = {
Please log in to edit this wiki.
+
            question: 'Chief! This page contains sneak peeks. Are you sure you ' +
Joining Clash of Clans Wiki is free, and it only takes a minute.
+
                      'want to enter?',
We hope that you sign in, and become a member of the community!
+
            yes: 'Yes, please',
 +
            no: 'No, let it be a surprise',
 +
            isSpoiler: function () {
 +
                return (-1 !== wgCategories.indexOf('Spoiler') &&
 +
                    Boolean($('.spoiler').length));
 +
            }
 +
        };
 +
    }
  
Click here to log in or create an account
+
    window.LockForums = {
You can view and copy the source of this page:
+
        expiryDays:    90,  // Number of days until forum is locked to new replies
 +
        expiryMessage: 'Forums are automatically locked when the most recent post is older than <expiryDays> days.',
 +
        warningDays:  14,  // Number of days until a warning is given to potential replies
 +
        ignoreDeletes: true, // Ignore deleted messages when calculating age of last post
 +
        warningPopup:  true, // Pop up a warning dialog that must be confirmed for posts on older forums
 +
        banners:      true, // Add a banner to the top of aged forums
 +
    };
  
 +
    /* Articles are interwiki links so that other wikis can use them. */
 +
    articles = [
 +
        'w:c:spottra:MediaWiki:Common.js/Numeral.js', // Defines num.format('<fmt>')
 +
        'w:c:spottra:MediaWiki:Common.js/AjaxGallery.js',
 +
        'u:dev:Countdown/code.js',
 +
        'u:dev:SpoilerAlert/code.js',
 +
        'u:dev:TopEditors/code.js',
 +
        'u:dev:WallGreetingButton/code.js',
 +
        'u:dev:ExtendedNavigation/code.js',
 +
        'u:dev:LockForums/code.js',
 +
        'u:dev:LockOldBlogs/code.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/RGBColor.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/Usernames.js',
 +
        'u:dev:UserTags/code.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/Sliders.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/GemCalculators.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/Experience.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/TroopInfo.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/BuildingInfo.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/AchievementInfo.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/Tabber2.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/ImageHover.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/CumulativeCosts.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/UnitComparator.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/ModeToggle.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/PageVerify.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/GorillaMan.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/Lugia.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/BadgeGenerator.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/Protection.js',
 +
        'w:c:clashofclans:MediaWiki:Common.js/AvailableBuildings.js',
 +
    ];
 +
    // Use Wikia's importArticles() function to load JavaScript files
 +
    window.importArticles({
 +
        type: 'script',
 +
        articles: articles
 +
    });
 +
    console.log('Site-wide JavaScript in MediaWiki:Common.js will load the ' +
 +
                'following JavaScript files:\n  ' + articles.join('\n  '));
  
function timeStamp_AttackStrategies_js() {
+
    // Moves Clash Royale link to page header
  return "2014.07.20 00:47 (UTC-7)";
+
    $('#ClashRoyaleLink').appendTo('header#WikiaPageHeader');
}
+
}(jQuery, mediaWiki, window.localStorage));
  
window.onload = function() {
+
// Change Random Page button to only go to pages in the mainspace
  attackStrategyReset();
+
    $('.wds-dropdown a[data-tracking=explore-random], ul.tools li a[data-name=random]').attr("href", "/wiki/Special:Random/main");
};
+
  
function attackStrategyFilter() {
+
/** Collapsible tables *********************************************************
   var minTH      = document.getElementById("min-town-hall").value;
+
*
   var maxTH      = document.getElementById("max-town-hall").value;
+
*  Description: Allows tables to be collapsed, showing only the header. See
   var minTrophies = document.getElementById("min-trophies").value;
+
*  http://www.mediawiki.org/wiki/Manual:Collapsible_tables.
   var maxTrophies = document.getElementById("max-trophies").value;
+
*  Maintainers: [[en:User:R. Koot]]
   var troopFilter = $('#troop-filter-text').html();
+
*/
  var filterType  = $('#troop-filter-type-text').html();
+
var autoCollapse    = 2;
  var troops;
+
var collapseCaption = 'hide';
 +
var expandCaption  = 'show';
 +
 +
function collapseTable(tableIndex) {
 +
   var Button = document.getElementById('collapseButton'  + tableIndex);
 +
   var Table  = document.getElementById('collapsibleTable' + tableIndex);
 +
 +
   if (!Table || !Button)
 +
      return false;
 +
 +
   var Rows = Table.rows;
 +
 +
   if (Button.firstChild.data == collapseCaption) {
 +
      for (var i = 1; i < Rows.length; i ++)
 +
        Rows[i].style.display = 'none';
  
  if (minTH === '')
+
       Button.firstChild.data = expandCaption;
       minTH = 0;
+
  }
   else
+
   else {
       minTH = Number(minTH);
+
       for (var i = 1; i < Rows.length; i ++)
 +
        Rows[i].style.display = Rows[0].style.display;
  
  if (maxTH === '')
+
       Button.firstChild.data = collapseCaption;
       maxTH = 99;
+
  else
+
      maxTH = Number(maxTH);
+
 
+
  if (minTrophies === '')
+
      minTrophies = 0;
+
  else
+
      minTrophies = Number(minTrophies);
+
 
+
  if (maxTrophies === '')
+
      maxTrophies = 999999;
+
  else
+
      maxTrophies = Number(maxTrophies);
+
 
+
  if (minTH < 0)
+
      minTH = 0;
+
 
+
  if (maxTH < minTH)
+
      maxTH = minTH;
+
 
+
  if (minTrophies < 0)
+
      minTrophies = 0;
+
 
+
  if (maxTrophies < minTrophies)
+
      maxTrophies = minTrophies;
+
 
+
  if (troopFilter.toLowerCase() === 'all')
+
      troops = true;
+
  else if (troopFilter.toLowerCase() === 'none')
+
      troops = false;
+
  else {
+
      troops = troopFilter.split(', ');
+
 
   }
 
   }
 +
}
 +
 +
function createCollapseButtons() {
 +
  var tableIndex      = 0;
 +
  var NavigationBoxes = new Object();
 +
  var Tables          = document.getElementsByTagName('table');
 +
 +
  for (var i = 0; i < Tables.length; i ++) {
 +
      if (hasClass(Tables[i], 'collapsible')) {
 +
        /* only add button and increment count if there is a header row
 +
            to work with */
 +
        var HeaderRow = Tables[i].getElementsByTagName('tr')[0];
  
  var tbl      = document.getElementById('attack-strategies-results');
+
        if (!HeaderRow)
  var tr        = tbl.getElementsByTagName('tr');
+
            continue;
  var troopList = troopInfo('list', 'trainable');
+
  
  for (var i = 1; i < tr.length; i ++) {
+
        var Header = HeaderRow.getElementsByTagName('th')[0];
      var td              = tr[i].getElementsByClassName('attack-strategy-hidden-field');
+
      var currMinTH      = Number(td[0].innerHTML);
+
      var currMaxTH      = Number(td[1].innerHTML);
+
      var currMinTrophies = Number(td[2].innerHTML);
+
      var currMaxTrophies = Number(td[3].innerHTML);
+
  
      if (currMinTH > maxTH ||
+
         if (!Header)
          currMaxTH < minTH ||
+
            continue;
          currMinTrophies > maxTrophies ||
+
          currMaxTrophies < minTrophies)
+
         $(tr[i]).css({'display': 'none'});
+
      else if (troops === true && filterType === 'Includes')
+
        $(tr[i]).css({'display': ''});
+
      else if (troops === false && filterType === 'Excludes')
+
        $(tr[i]).css({'display': ''});
+
      else if (troops === true && filterType === 'Only')
+
        $(tr[i]).css({'display': ''});
+
      else if (troops === false && filterType === 'Includes')
+
        $(tr[i]).css({'display': 'none'});
+
      else if (troops === true && filterType === 'Excludes')
+
        $(tr[i]).css({'display': 'none'});
+
      else if (troops === false && filterType === 'Only')
+
        $(tr[i]).css({'display': 'none'});
+
      else if (filterType === 'Includes') {
+
        var include = false;
+
  
         for (var j = 0; j < troops.length; j ++) {
+
         NavigationBoxes[tableIndex] = Tables[i];
            var idx = tableIndex(troops[j]);
+
        Tables[i].setAttribute('id', 'collapsibleTable' + tableIndex);
 
+
            if (idx >= 0 && td[idx].innerHTML === 'Yes') {
+
        var Button    = document.createElement('span');
              include = true;
+
        var ButtonLink = document.createElement('a');
              break;
+
        var ButtonText = document.createTextNode(collapseCaption);
             }
+
         }
+
        // Styles are declared in [[MediaWiki:Common.css]]
 
+
        Button.className = 'collapseButton';
         $(tr[i]).css({'display': (include ? '' : 'none')});
+
 +
        ButtonLink.style.color = Header.style.color;
 +
        ButtonLink.setAttribute('id', 'collapseButton' + tableIndex);
 +
        ButtonLink.setAttribute('href',
 +
             "javascript:collapseTable(" + tableIndex + ");" );
 +
         ButtonLink.appendChild(ButtonText);
 +
 +
         Button.appendChild(document.createTextNode('['));
 +
        Button.appendChild(ButtonLink);
 +
        Button.appendChild(document.createTextNode(']'));
 +
 +
        Header.insertBefore(Button, Header.childNodes[0]);
 +
        tableIndex ++;
 
       }
 
       }
       else if (filterType === 'Excludes') {
+
  }
         var include = true;
+
 +
  for (var i = 0; i < tableIndex; i ++) {
 +
       if (hasClass(NavigationBoxes[i], 'collapsed') ||
 +
        (tableIndex >= autoCollapse &&
 +
          hasClass(NavigationBoxes[i], 'autocollapse')))
 +
        collapseTable(i);
 +
      else if (hasClass(NavigationBoxes[i], 'innercollapse')) {
 +
         var element = NavigationBoxes[i];
  
         for (var j = 0; j < troops.length; j ++) {
+
         while (element = element.parentNode) {
            var idx = tableIndex(troops[j]);
+
             if (hasClass(element, 'outercollapse')) {
 
+
               collapseTable(i);
             if (idx >= 0 && td[idx].innerHTML === 'Yes') {
+
               include = false;
+
 
               break;
 
               break;
 
             }
 
             }
 
         }
 
         }
 
        $(tr[i]).css({'display': (include ? '' : 'none')});
 
 
       }
 
       }
      else if (filterType === 'Only') {
 
        var include = false;
 
 
        for (var j = 0; j < troops.length; j ++) {
 
            var idx = tableIndex(troops[j]);
 
 
            if (idx >= 0 && td[idx].innerHTML === 'Yes') {
 
              include = true;
 
              break;
 
            }
 
        }
 
 
        if (include) {
 
            for (var j = 0; j < troopList.length; j ++) {
 
              var idx = tableIndex(troopList[j]);
 
 
              if (!hasTroop(troopList[j]) && idx >= 0 && td[idx].innerHTML === 'Yes') {
 
                  include = false;
 
                  break;
 
              }
 
            }
 
        }
 
 
        $(tr[i]).css({'display': (include ? '' : 'none')});
 
      }
 
      else {
 
        $(tr[i]).css({'display': ''});
 
      }
 
  }
 
 
  function hasTroop(trooptype) {
 
      if (troops === true || troops === false)
 
        return troops;
 
 
      return troops.indexOf(trooptype) >= 0;
 
  }
 
 
  function tableIndex(trooptype) {
 
      var idx = $('#troop-filter-selector option[value="' + trooptype + '"]').index();
 
      return (idx >= 0 ? idx + 4 : idx);
 
 
   }
 
   }
 
}
 
}
  
function attackStrategyReset() {
+
addOnloadHook(createCollapseButtons);
  document.getElementById("min-town-hall").value = 1;
+
  document.getElementById("max-town-hall").value = '';
+
/** Test if an element has a certain class ********************************
   document.getElementById("min-trophies").value = 0;
+
*
   document.getElementById("max-trophies").value = '';
+
* Description: Uses regular expressions and caching for better performance.
  document.getElementById("troop-filter-text").innerHTML = 'All';
+
* Maintainers: [[User:Mike Dillon]], [[User:R. Koot]], [[User:SG]]
  document.getElementById("troop-filter-type-text").innerHTML = 'Includes';
+
*/
  document.getElementById("troop-filter-type-text").title =
+
      'Will show all attack strategies that include at least one of the selected troop types.';
+
var hasClass = (function() {
   attackStrategyFilter();
+
   var reCache = {};
}
+
   return function(element, className) {
 +
      return ( reCache[className] ? reCache[className] :
 +
        (reCache[className] = new RegExp( "(?:\\s|^)" + className +
 +
        "(?:\\s|$)" ) ) ).test(element.className);
 +
   };
 +
})();
  
function troopFilterInitiate() {
+
function hasClassTest(element, className) {
   doTroopSelect($('#troop-filter-text').html());
+
   // No reason to have two functions that do the same thing
   $('#troop-filter-type').val($('#troop-filter-type-text').html());
+
   // return element.className.indexOf(className) != -1;
   $('#troop-background').addClass('window-visible');
+
   return hasClass(element, className);
 
}
 
}
 
function troopFilterCancel() {
 
  $('#troop-background').removeClass('window-visible');
 
}
 
 
function troopFilterExecute() {
 
  var select    = $('#troop-filter-selector');
 
  var all      = true;
 
  var none      = true;
 
  var selection = [];
 
 
  $('option', select).each(function(idx) {
 
      if ($(this).prop('selected')) {
 
        selection.push($(this).val());
 
        none = false;
 
      }
 
      else
 
        all = false;
 
  });
 
 
  if (none)
 
      $('#troop-filter-text').html('None');
 
  else if (all)
 
      $('#troop-filter-text').html('All');
 
  else
 
      $('#troop-filter-text').html(selection.join(', '));
 
 
  $('#troop-filter-type-text').html($('#troop-filter-type').val());
 
 
  switch ($('#troop-filter-type').val()) {
 
      case 'Includes':
 
        $('#troop-filter-type-text').prop('title',
 
            'Will show all attack strategies that include at least one of the selected troop types.');
 
        break;
 
      case 'Excludes':
 
        $('#troop-filter-type-text').prop('title',
 
            'Will show all attack strategies that do not include any of the selected troop types.');
 
        break;
 
      case 'Only':
 
        $('#troop-filter-type-text').prop('title',
 
            'Will show all attack strategies that include only the selected troop types.');
 
        break;
 
  }
 
 
  troopFilterCancel();
 
}
 
 
function troopSelectNone() {
 
  doTroopSelect('none');
 
}
 
 
function troopSelectAll() {
 
  doTroopSelect('all');
 
}
 
 
function doTroopSelect(selection) {
 
  var select = $('#troop-filter-selector');
 
 
  if (selection.toLowerCase() === 'all')
 
      $('option', select).prop('selected', true);
 
  else if (selection.toLowerCase() === 'none')
 
      $('option', select).prop('selected', false);
 
  else {
 
      var selects = selection.split(', ');
 
 
      $('option', select).each(function(idx) {
 
        $(this).prop('selected', selects.indexOf($(this).val()) >= 0);
 
      });
 
  }
 
}
 
 
Return to MediaWiki:Common.js/AttackStrategies.js.
 

Latest revision as of 11:11, 15 November 2018

/* Any JavaScript here will be loaded for all users on every page load. */
 
(function ($, mw, store) {
    "use strict";
    var articles;
 
    if (store && store.getItem('commonjs')) {
        console.log('You have chosen to disable site-wide JavaScript ' +
                    'in MediaWiki:Common.js. Please remove \'commonjs\' ' +
                    'from localStorage to re-enable site-wide JavaScript.');
        return;
    }
 
    window.UserTagsJS = {
	modules: {},
	tags: {
           heroicuser:  { u:'Most Heroic Contributor' },
           imageeditor: { u:'Image Editor' },
           retired: { u:'Retired Clasher' },
        }
    };
    UserTagsJS.modules.custom        = {};
    UserTagsJS.modules.inactive      = 30;
    UserTagsJS.modules.newuser       = true;
    UserTagsJS.modules.autoconfirmed = true;
 
    UserTagsJS.modules.mwGroups = [
        'bureaucrat',
        'sysop',
        'chatmoderator',
        'threadmoderator',
        'rollback',
        'patroller',
        'bannedfromchat',
        'bot',
        'bot-global',
    ];

    UserTagsJS.modules.metafilter = {
        bureaucrat:      ['founder'],
        sysop:           ['founder', 'bureaucrat'],
        chatmoderator:   ['founder', 'bureaucrat', 'sysop'],
        threadmoderator: ['founder', 'bureaucrat', 'sysop', 'chatmoderator'],
        imageeditor:     ['founder', 'bureaucrat', 'sysop', 'chatmoderator', 'threadmoderator'],
        rollback:        ['founder', 'bureaucrat', 'sysop', 'chatmoderator', 'threadmoderator',
                          'imageeditor'],
    };
 
    UserTagsJS.modules.custom = {
        'FaceBound': ['imageeditor'], // Image Editor
    };

    if (typeof(window.SpoilerAlert) === 'undefined') {
        window.SpoilerAlert = {
            question: 'Chief! This page contains sneak peeks. Are you sure you ' +
                      'want to enter?',
            yes: 'Yes, please',
            no: 'No, let it be a surprise',
            isSpoiler: function () {
                return (-1 !== wgCategories.indexOf('Spoiler') &&
                    Boolean($('.spoiler').length));
            }
        };
    }

    window.LockForums = {
        expiryDays:    90,  // Number of days until forum is locked to new replies
        expiryMessage: 'Forums are automatically locked when the most recent post is older than <expiryDays> days.',
        warningDays:   14,   // Number of days until a warning is given to potential replies
        ignoreDeletes: true, // Ignore deleted messages when calculating age of last post
        warningPopup:  true, // Pop up a warning dialog that must be confirmed for posts on older forums
        banners:       true, // Add a banner to the top of aged forums
    };

    /* Articles are interwiki links so that other wikis can use them. */
    articles = [
        'w:c:spottra:MediaWiki:Common.js/Numeral.js', // Defines num.format('<fmt>')
        'w:c:spottra:MediaWiki:Common.js/AjaxGallery.js',
        'u:dev:Countdown/code.js',
        'u:dev:SpoilerAlert/code.js',
        'u:dev:TopEditors/code.js',
        'u:dev:WallGreetingButton/code.js',
        'u:dev:ExtendedNavigation/code.js',
        'u:dev:LockForums/code.js',
        'u:dev:LockOldBlogs/code.js',
        'w:c:clashofclans:MediaWiki:Common.js/RGBColor.js',
        'w:c:clashofclans:MediaWiki:Common.js/Usernames.js',
        'u:dev:UserTags/code.js',
        'w:c:clashofclans:MediaWiki:Common.js/Sliders.js',
        'w:c:clashofclans:MediaWiki:Common.js/GemCalculators.js',
        'w:c:clashofclans:MediaWiki:Common.js/Experience.js',
        'w:c:clashofclans:MediaWiki:Common.js/TroopInfo.js',
        'w:c:clashofclans:MediaWiki:Common.js/BuildingInfo.js',
        'w:c:clashofclans:MediaWiki:Common.js/AchievementInfo.js',
        'w:c:clashofclans:MediaWiki:Common.js/Tabber2.js',
        'w:c:clashofclans:MediaWiki:Common.js/ImageHover.js',
        'w:c:clashofclans:MediaWiki:Common.js/CumulativeCosts.js',
        'w:c:clashofclans:MediaWiki:Common.js/UnitComparator.js',
        'w:c:clashofclans:MediaWiki:Common.js/ModeToggle.js',
        'w:c:clashofclans:MediaWiki:Common.js/PageVerify.js',
        'w:c:clashofclans:MediaWiki:Common.js/GorillaMan.js',
        'w:c:clashofclans:MediaWiki:Common.js/Lugia.js',
        'w:c:clashofclans:MediaWiki:Common.js/BadgeGenerator.js',
        'w:c:clashofclans:MediaWiki:Common.js/Protection.js',
        'w:c:clashofclans:MediaWiki:Common.js/AvailableBuildings.js',
    ];
    // Use Wikia's importArticles() function to load JavaScript files
    window.importArticles({
        type: 'script',
        articles: articles
    });
    console.log('Site-wide JavaScript in MediaWiki:Common.js will load the ' +
                'following JavaScript files:\n   ' + articles.join('\n   '));

    // Moves Clash Royale link to page header
    $('#ClashRoyaleLink').appendTo('header#WikiaPageHeader');
}(jQuery, mediaWiki, window.localStorage));

// Change Random Page button to only go to pages in the mainspace
    $('.wds-dropdown a[data-tracking=explore-random], ul.tools li a[data-name=random]').attr("href", "/wiki/Special:Random/main");

/** Collapsible tables *********************************************************
 *
 *  Description: Allows tables to be collapsed, showing only the header. See
 *  http://www.mediawiki.org/wiki/Manual:Collapsible_tables.
 *  Maintainers: [[en:User:R. Koot]]
 */
var autoCollapse    = 2;
var collapseCaption = 'hide';
var expandCaption   = 'show';
 
function collapseTable(tableIndex) {
   var Button = document.getElementById('collapseButton'   + tableIndex);
   var Table  = document.getElementById('collapsibleTable' + tableIndex);
 
   if (!Table || !Button)
      return false;
 
   var Rows = Table.rows;
 
   if (Button.firstChild.data == collapseCaption) {
      for (var i = 1; i < Rows.length; i ++)
         Rows[i].style.display = 'none';

      Button.firstChild.data = expandCaption;
   }
   else {
      for (var i = 1; i < Rows.length; i ++)
         Rows[i].style.display = Rows[0].style.display;

      Button.firstChild.data = collapseCaption;
   }
}
 
function createCollapseButtons() {
   var tableIndex      = 0;
   var NavigationBoxes = new Object();
   var Tables          = document.getElementsByTagName('table');
 
   for (var i = 0; i < Tables.length; i ++) {
      if (hasClass(Tables[i], 'collapsible')) {
         /* only add button and increment count if there is a header row
            to work with */
         var HeaderRow = Tables[i].getElementsByTagName('tr')[0];

         if (!HeaderRow)
            continue;

         var Header = HeaderRow.getElementsByTagName('th')[0];

         if (!Header)
            continue;

         NavigationBoxes[tableIndex] = Tables[i];
         Tables[i].setAttribute('id', 'collapsibleTable' + tableIndex);
 
         var Button     = document.createElement('span');
         var ButtonLink = document.createElement('a');
         var ButtonText = document.createTextNode(collapseCaption);
 
         // Styles are declared in [[MediaWiki:Common.css]]
         Button.className = 'collapseButton';
 
         ButtonLink.style.color = Header.style.color;
         ButtonLink.setAttribute('id', 'collapseButton' + tableIndex);
         ButtonLink.setAttribute('href',
            "javascript:collapseTable(" + tableIndex + ");" );
         ButtonLink.appendChild(ButtonText);
 
         Button.appendChild(document.createTextNode('['));
         Button.appendChild(ButtonLink);
         Button.appendChild(document.createTextNode(']'));
 
         Header.insertBefore(Button, Header.childNodes[0]);
         tableIndex ++;
      }
   }
 
   for (var i = 0; i < tableIndex; i ++) {
      if (hasClass(NavigationBoxes[i], 'collapsed') ||
         (tableIndex >= autoCollapse &&
          hasClass(NavigationBoxes[i], 'autocollapse')))
         collapseTable(i);
      else if (hasClass(NavigationBoxes[i], 'innercollapse')) {
         var element = NavigationBoxes[i];

         while (element = element.parentNode) {
            if (hasClass(element, 'outercollapse')) {
               collapseTable(i);
               break;
            }
         }
      }
   }
}

addOnloadHook(createCollapseButtons);
 
/** Test if an element has a certain class ********************************
 *
 * Description: Uses regular expressions and caching for better performance.
 * Maintainers: [[User:Mike Dillon]], [[User:R. Koot]], [[User:SG]]
 */
 
var hasClass = (function() {
   var reCache = {};
   return function(element, className) {
      return ( reCache[className] ? reCache[className] :
         (reCache[className] = new RegExp( "(?:\\s|^)" + className +
         "(?:\\s|$)" ) ) ).test(element.className);
   };
})();

function hasClassTest(element, className) {
   // No reason to have two functions that do the same thing
   // return element.className.indexOf(className) != -1;
   return hasClass(element, className);
}