[ Disclaimer, Create new user --- Wiki markup help, Install P99 ]
MediaWiki:Common.js
From Project 1999 Wiki
Note: After saving, you may have to bypass your browser's cache to see the changes.
- Firefox / Safari: Hold Shift while clicking Reload, or press either Ctrl-F5 or Ctrl-R (⌘-R on a Mac)
- Google Chrome: Press Ctrl-Shift-R (⌘-Shift-R on a Mac)
- Internet Explorer: Hold Ctrl while clicking Refresh, or press Ctrl-F5
- Opera: Clear the cache in Tools → Preferences
/* Any JavaScript here will be loaded for all users on every page load. */
importScript('MediaWiki:Simple-lightbox.min.js');
importScript('MediaWiki:Polyfills.js');
importScript('MediaWiki:Zones.js');
// **********************************
// Add localStorage helper functions
// **********************************
/**
* Basic "state getter": checks localStorage for *stateKey*, then return the
* value for *pageName* (if any) found on that object.
*/
var getPageState = function(pageName, stateKey) {
// Get the state for all pages for this key
var allPageStates = JSON.parse(localStorage.getItem(stateKey) || '{}');
// Extract just the state for this page (if any)
return allPageStates[pageName];
};
/**
* Returns the state data stored for the provided stateKey and the current page.
* For instance, getStateByPage('checkbox-status') would return the checkbox\
* status state for the current page.
*/
window.getStateByPage = function(stateKey) {
var pageName = location.pathname.substr(1); // ditch the leading "/"
return getPageState(pageName, stateKey);
};
/**
* Return the global state for a provided state key
* (works just like getStateByPage, but for states that don't care
* about which page you are on)
*/
window.getGlobalState = function(stateKey) {
return getPageState('__global', stateKey);
};
/**
* Basic "state setter" function
*/
var setPageState = function(pageName, stateKey, state) {
// Get the state for this key (for all pages) out of local storage
var allPageStates = JSON.parse(localStorage.getItem(stateKey) || '{}');
// Set the state only for this page
allPageStates[pageName] = state;
// Put the state for the stateKey (for all pages) back into local storage
localStorage.setItem(stateKey, JSON.stringify(allPageStates));
};
/**
* Sets the state data stored for the provided stateKey and the current page.
* For instance, setStateByPage('checkbox-status', {a: 'b'}) would set the
* checkbox status state for the current page to an object with a key of "a" and
* value of "b".
*/
window.setStateByPage = function(stateKey, state) {
var pageName = location.pathname.substr(1); // ditch the leading "/"
setPageState(pageName, stateKey, state);
};
window.setGlobalState = function(stateKey, state) {
return setPageState('__global', stateKey, state);
};
// *******************************
/* p1999wiki.js
* written by http://wiki.project1999.com/User:Ravhin
* last update: 7 January, 2018 by Loramin
*/
$(function() {
var hideDelay = 0;
var trigDelay = 250;
var hideTimer = null;
var ajax = null;
var currentPosition = { left: '0px', top: '0px' };
// One instance that's reused to show info for the current person
var container = $('<div id="itemHoverContainer">'
+ '<div id="HoverContent"></div>'
+ '</div>');
$('body').append(container);
/* --- hoverbox for item/mob, currently only used in magelo --- */
// Determine which "a" elements should trigger the item stats mouseover
var $mouseoverTargets = $('span.ih a');
var isItemCategory = document.title.startsWith('Category:') && document.title.includes('Equipment - Project 1999 Wiki') &&
!document.title.includes('Worshiper Equipment');
if (isItemCategory) {
// Include the category's item list along with ".ih" links
$mouseoverTargets = $mouseoverTargets.add('.mw-content-ltr a');
}
$mouseoverTargets = $mouseoverTargets.filter(function(i, a) {
// Don't add hover to links like "next 200"
return !$(a).attr('href').startsWith('/Special:') &&
!$(a).attr('href').includes('title=Category:')
});
$mouseoverTargets.on('mouseover', function()
{
var $this = $(this);
var itemname = $this.attr('title');
if (itemname == '' || itemname == 'undefined')
return;
if (hideTimer)
clearTimeout(hideTimer);
if ($this.parents('div.mw-content-ltr').length) {
var pos = $this.offset();
var width = $this.width();
container.css({
left: pos.left + 5 + 'px',
top: pos.top + 5 + 'px'
});
}
$(this).trigger('mousemove');
$('#itemHoverContent').html(' ');
//$('#itemHoverContent').html('<div class="itemtopbg"><div class="itemtitle">Loading...</div></div>'
// + '<div class="itembg" style="min-height:50px;"><div class="itemdata">'
// + '<div class="itemicon" style="float:right;"><img alt="" src="/images/Ajax_loader.gif" border="0"></div>'
// + '<p></p></div></div><div class="itembotbg"></div>');
if (ajax)
{
ajax.abort();
ajax = null;
}
ajax = $.ajax({
url: window.location.protocol +
'//wiki.project1999.com/index.php/Special:AjaxHoverHelper/' + itemname,
cacheResponse: true,
success: function(html)
{
var $html = $(html);
$('#itemHoverContent').html($html[2]).prepend($html[0]).prepend($html[1]);
}
});
container.css('display', 'block');
//container.fadeIn('fast');
}); //on mouseover
$('span.ih a').on('mouseout', function()
{
if (hideTimer)
clearTimeout(hideTimer);
hideTimer = setTimeout(function()
{
container.css('display', 'none');
//container.fadeOut('fast');
}, hideDelay);
});
$('span.ih a').mousemove(function(e){
var mousex = e.pageX + 20; //Get X coodrinates
var mousey = e.pageY + 20; //Get Y coordinates
var tipWidth = container.width(); //Find width of tooltip
var tipHeight = container.height(); //Find height of tooltip
//Distance of element from the right edge of viewport
var tipVisX = $(window).width() - (mousex + tipWidth);
//Distance of element from the bottom of viewport
var tipVisY = $(window).height() - (mousey + tipHeight);
if ( tipVisX < 20 ) { //If tooltip exceeds the X coordinate of viewport
if( tipWidth > e.pageX - 20 ){
mousex = 0;
} else {
mousex = e.pageX - tipWidth - 20;
}
} if ( tipVisY < 20 ) { //If tooltip exceeds the Y coordinate of viewport
mousey = e.pageY - tipHeight - 20;
}
container.css({ top: mousey, left: mousex });
});
// Allow mouse over of details without hiding details
$('#itemHoverContainer').mouseover(function()
{
if (hideTimer)
clearTimeout(hideTimer);
});
// Hide after mouseout
$('#itemHoverContainer').mouseout(function()
{
if (hideTimer)
clearTimeout(hideTimer);
hideTimer = setTimeout(function()
{
container.css('display', 'none');
//container.fadeOut('fast');
}, hideDelay);
});
// magelo non-ajax item hover, but move box with mouse
$('.magelohb').mousemove(function(e){
var childContainer = $(this).children('span.hb');
var tipWidth = childContainer.width(); //Find width of tooltip
var tipHeight = childContainer.height(); //Find height of tooltip
var mousex = e.pageX + 20; //Get X coodrinates
var mousey = e.pageY + 20; //Get Y coordinates
//Distance of element from the right edge of viewport
var tipVisX = $(window).width() - (mousex + tipWidth - 20);
//Distance of element from the bottom of viewport
var tipVisY = $(window).height() - (mousey + tipHeight - 20);
if ( tipVisX < 20 ) { //If tooltip exceeds the X coordinate of viewport
if( tipWidth > e.pageX - 20){
mousex = 0;
} else {
mousex = e.pageX - tipWidth - 20;
}
} if ( tipVisY < 20 ) { //If tooltip exceeds the Y coordinate of viewport
mousey = e.pageY - tipHeight - 20;
}
childContainer.css({ top: mousey, left: mousex, 'z-index':'999' });
});
// change to position:fixed on all hover divs if we have JS active
// otherwise leave as position:absolute so the stationary hovers are near their items
$('.magelohb span.hb').each(function(i) {
$(this).css({'position':'fixed'});
});
// Chrome no longer displays alt text when an image is hovered over. However the wiki only has
// alt attributes for images, not titles. This fixes that by converting alt => title
$('img[alt]').each(function (i, img) {
$(img).attr('title', $(img).attr('alt'));
});
// Fashion for item pages
var extractFashionHtml = function(html) {
return $(html).find('.fashion_show, .primary_secondary_show').map(function(i, el) {
var $el = $(el);
var data = $el.data();
data.race = $el.find('.fashion_race').html();
if ($el.is('.fashion_show')) {
data.armor = $el.find('.fashion_armor').html();
}
return data;
}).toArray();
};
var getFashionShows = function(fashionCategory) {
var url = '/Category:Fashion: ' + fashionCategory;
return $.get(url).then(extractFashionHtml);
};
var getItemPageShows = function() {
var fashionCategories =
$('#catlinks li a')
.map(function(i, a) { return $(a).text(); })
.filter(function(i, text) { return text.startsWith('Fashion:'); })
.map(function(i, text) { return text.substr('Fashion: '.length); });
var fashion = fashionCategories[0];
if (!fashion) return $.when();
var tint = fashionCategories[1];
return getFashionShows(fashion).then(function(shows) {
var sameTint = [];
var otherTint = [];
shows.forEach(function(show) {
var isHeld = show.primaryFashion || show.secondaryFashion;
var bothHaveSameTint = show.tint === tint;
var bothHaveNoTint = !(show.tint || tint);
if (isHeld || bothHaveSameTint || bothHaveNoTint) sameTint.push(show);
else otherTint.push(show);
});
return { matches: sameTint, partialMatches: otherTint, fashion: fashion, tint: tint };
});
}
var addFashionSection = function(shows, isFullMatch) {
var preface = isFullMatch
? '<h2>Fashion/Appearance</h2>'
: '<div>Fashion images with the wrong "tint" (i.e. coloring) which ' +
'can only be used to get a general sense of the item\'s ' +
'appearance:</div>';
// Don't show the explanatory text if there are no shows to explain
if (!shows.length && !isFullMatch) preface = '';
var $ul = $('<ul>').append(shows.map(function(show) {
var img = isFullMatch
? '<br/><img style="max-height: 100px; max-width: 100px;" src="/images/' +
show.file.replace(/ /g, '_') + '"/>'
: '';
return '<li class="fashion-link" data-file="' + show.file +'">' +
'<a href="#">' + show.gender + ' ' + show.race + img + '</a></li>';
}));
$('#itemfashion').before($('<div>' + preface + '</div>').append($ul));
};
var addFashionSections = function() {
getItemPageShows().then(function(pageShows) {
if(!pageShows) return;
var matches = pageShows.matches || [];
var partialMatches = pageShows.partialMatches || [];
if (pageShows.matches.length || pageShows.partialMatches.length)
addFashionSection(pageShows.matches, true);
if (pageShows.partialMatches.length)
addFashionSection(pageShows.partialMatches, false);
});
};
addFashionSections();
//*****************************************
// Add class-based filtering to item tables
//*****************************************w
// Determine whether or not a provided row should be shown for the provided
// class abbreviation (eg. "BRD")
var isRowShown = function($tr, classAbbrev) {
// Extract classes (and races)
var classText = $tr.find('td').eq(3).text().split('Class:')[1];
if (!classText) return true; // Ignore (don't filter) rows without class text
// remove "Race: " part (if any) and upper-case text
classText = classText.split('Race:')[0] || classText;
classText = classText.toUpperCase();
// determine matching text
var isMatch = classText.includes(classAbbrev);
var isAllMatch = classText.includes('ALL');
var isExcept = classText.includes('ALL EXCEPT');
// determine matches
if (isMatch && !isExcept) return true; // (eg. BRD in "BRD")
if (!isMatch && isExcept) return true; // (eg. BRD in "ALL EXCEPT WIZ")
if (!isExcept && isAllMatch) return true; // (eg. BRD in "ALL")
return false;
};
var scrollToTable = function($table) {
window.setTimeout(function() {
$('html, body').animate({ scrollTop: ($table.offset().top) }, 200);
}, 100);
};
// Filter the provided table to only display rows for the provided class
// abbreviation
var filterTable = function($table, classAbbrev) {
$table.find('tr').each(function (i, tr) {
var $tr = $(tr);
var rowIsShown = isRowShown($tr, classAbbrev);
$tr.toggle(rowIsShown);
});
scrollToTable($table);
addFilterLink($table, false);
$('.itemsUnfilterLink').click(function() {
unfilterTable($table);
});
alert('Filtered to only show rows containing ' + classAbbrev + ' gear.');
};
// Restore a table to its previous, un-filtered state
var unfilterTable = function($table) {
$table.find('tr').show();
addFilterLink($table, true);
scrollToTable($table);
};
// When a user clicks on a table class filter link, handle it by asking them
// which class (and then filtering the table for that class)
var handleItemFilterLinkClick = function(e) {
var promptMessage = 'Please enter the three-letter abbreviation for the ' +
'class you want to filter by (eg. "brd" for "Bard").';
var $table = $(e.target).closest('table');
var classAbbrev = prompt(promptMessage).toUpperCase();
if (!classAbbrev || classAbbrev.length !== 3 || classAbbrev === 'ALL') {
alert('A 3-digit abbreviation wasn\'t entered (or "All" was entered); ' +
'filtering disabled');
unfilterTable($table);
return false;
}
filterTable($table, classAbbrev);
};
// Adds either a filter or unfilter link (as determined by showFilter) to the
// provided table
var addFilterLink = function($table, showFilter) {
var $statsHeaderCells = $table.find('th:contains("Stats")');
var filterType = showFilter ? 'Filter' : 'Unfilter';
$statsHeaderCells.html('Stats <span style="float:right">' +
'<a style="text-decoration: underline" class="items' + filterType + 'Link" href="#">' +
filterType + (showFilter ? ' by Class' : '') + '</a></span>');
var $link = $statsHeaderCells.find('.items' + filterType + 'Link');
if (showFilter) $link.click(handleItemFilterLinkClick);
else $link.click(function() { unfilterTable($table); })
};
// Add class filtering links to all item tables
var addItemFilteringLinks = function() {
var $tables = $('table th:contains("Item Name")').closest('table');
$tables.each(function(i, table) {
var $table = $(table);
// Make sure it has both "Item Name" and "Stats" columns
if (!$table.has('th:contains("Stats")')) return;
addFilterLink($table, true);
});
};
addItemFilteringLinks();
//*****************************************
// End class-based filtering to item tables
//*****************************************
// Add No-Drop-Based filtering to the class equipment pages
if (window.location.pathname.includes('Special:ClassSlotEquip')) {
// Add checkboxes UI to the page
$('table')
.before('<label><input id="showNoDrop" type="checkbox" checked/> Show No Drop</label> ' +
'<label><input id="showDroppable" type="checkbox" checked/> Show Droppable</label>' +
'| <label><input id="showEffect" type="checkbox" checked/> Show With Effects</label>' +
'<label><input id="showNoEffect" type="checkbox" checked/> Show Without Effects</label>');
// Handle when drop/no drop box is checked
$('#showNoDrop, #showDroppable').change(function() {
var showNoDrop = $('#showNoDrop').is(':checked');
var showDroppable = $('#showDroppable').is(':checked');
// NOTE: Some tables are weird and don't keep their TRs in THEAD
// .... but those rows do have an old bgcolor="#cccccc" attribute
// that we can use to identify (and not hide) them
$('tbody tr[bgcolor!=#cccccc]').each(function(i, el) {
var text = $(el).find('td:eq(0) .itemdata').text();
var isNoDrop = text.includes('NO DROP');
$(el).toggle((showNoDrop && isNoDrop) || (showDroppable && !isNoDrop));
});
});
/*
Problem: the event handler needs to be merged so unchecking one box (eg. effect) doesn't undo the other (eg. no drop)
// Handle when effect/no effect box is checked
$('#showNoEfefct, #showEffect').change(function() {
var showNoEffect = $('#showNoEffect').is(':checked');
var showEffect = $('#showEffect').is(':checked');
// NOTE: Some tables are weird and don't keep their TRs in THEAD
// .... but those rows do have an old bgcolor="#cccccc" attribute
// that we can use to identify (and not hide) them
$('tbody tr[bgcolor!=#cccccc]').each(function(i, el) {
var text = $(el).find('td:eq(0) .itemdata').text();
var hasEffect = text.includes('NO DROP');
$(el).toggle((showEffect && hasEffect) || (showNoEffect && !hasEffect));
});
});
*/
}
// Generic Table Filtering (for Template:TableFilterCheckbox)
$('.table-filter-checkbox-container').each(function(i, el) {
var $container = $(el);
var matchSelector = $container.data('match');
var text = $container.text();
$container.html('<label><input class="table-filter-checkbox" type="checkbox" ' +
'value="' + matchSelector + '" checked />' + text + '</label>');
});
var shouldRowBeShown = function(tr) {
var $tr = $(tr);
// Check all the checkboxes to see if any given row should appear
// TODO: Instead of checking *every* checkbox, check ones in the same .filter-group
return $('.table-filter-checkbox')
.toArray()
.reduce(function(isShown, checkbox) {
var matchSelector = $(checkbox).val();
var matches = $tr.is(matchSelector) ||
!!$tr.has(matchSelector).length;
var isChecked = $(checkbox).attr('checked');
return isShown && !!(isChecked || (!isChecked && !matches));
}, true);
}
$('body').on('change', '.table-filter-checkbox', function(e) {
$('table').show();
$('table:not(.toc) tbody tr:not([bgcolor="#cccccc"])').each(function(i, tr) {
$(tr).toggle(shouldRowBeShown(tr));
});
// If all of a table's non-header rows are hidden, hide it
$('table').filter(function(i, table) {
return !$(table).has('tr:visible:not([bgcolor="#cccccc"])').length;
}).hide();
});
// Convert youtube template divs into actual iframes
$('.youtube-placeholder').each(function(i, placeholder) {
var $placeholder = $(placeholder);
var data = $placeholder.data();
var url = data.url;
// Youtube gets mad if you try to embed watch URLs
// @see https://stackoverflow.com/questions/25661182/embed-youtube-video-refused-to-display-in-a-frame-because-it-set-x-frame-opti
//if (url.includes('/watch?') url = url.replace('/watch?', '/embed?');
// TODO: get height/width from template?
$placeholder.replaceWith(
'<iframe ' +
'width="' + (data.width || '') + '" ' +
'height="' + (data.height || '') + '" ' +
'src="' + url + '" ' +
'frameborder="0" ' +
'allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" ' +
'allowfullscreen' +
'></iframe>'
);
});
importScript('MediaWiki:CheckboxLists.js');
importScript('MediaWiki:LocMaps.js');
var fullTitle = $('title').text();
var title = fullTitle.substr(0, fullTitle.length - ' - Project 1999 Wiki'.length);
switch(title) {
// Give the Per-Level Hunting Guide Page its own JS
case 'Per-Level Hunting Guide':
importScript('MediaWiki:HuntingGuide.js');
break;
// The item category search also needs special JS
case 'Item Category Search':
importScript('MediaWiki:ItemCategorySearch.js');
break;
// So does the Solo Artist Challenge
case 'Solo Artist Challenge':
importScript('MediaWiki:SoloArtistChallenge.js');
break;
case 'Treasure Hunting Guide':
importScript('MediaWiki:TreasureHuntingGuide.js');
break;
case 'Buff Lines':
importScript('MediaWiki:BuffLines.js');
break;
case 'FashionQuest Finder':
importScript('MediaWiki:FashionQuest.js');
break;
case 'Mobs By Level':
// Basic DOM manipulation (since the wiki won't let us add <input> tags in the wiki text
$('#placeholder')
.replaceWith(
'<form id="form">' +
'Class: <input id="class" style="width: 8em" value="Warrior" /> ' +
'Level: <input id="level" style="width: 4em" /> ' +
'<input type="submit"/>' +
'</form>'
);
$('#form').submit(function() {
var clazz = $('#class').val();
var level = $('#level').val();
window.location = 'https://wiki.project1999.com/index.php?title=Special:Search&limit=500&offset=0&redirs=0&profile=default&search=%22Level%5C%3A%5C+' +
level + '%22+-%22Shopkeeper%22+-%22Merchant%22+%22Class%5C%3A%5C+'+ clazz + '%22+-"startMageloProfile"';
return false;
});
break;
case 'Patch Notes':
// Let users control patch note width and how
// the table of contents is shown
var setNotesColumns = function(cols) { $('#notesWrapper').css('width', cols ? cols + 'em' : ''); };
var toggleNotRelevant =function(isChecked) {
$('#notesWrapper').find(':not(:visible)').show()
if (isChecked) return;
$('#notesWrapper').children().filter(function(i, el) {
var isRelevant = $(el).is('.relevant');
$(el).toggle(isRelevant);
// Show the patch header also
if (isRelevant) $(el).prevUntil('h3').last().prev().show();
})
};
var toggleTableOfContents = function(isChecked) { $('#toc').toggle(isChecked); };
var togglePatchHeaders = function(isChecked) { $('.toclevel-4').toggle(isChecked); };
var notesWidth = getStateByPage('notes-width') || '';
var showTableOfContents = getStateByPage('show-table-of-contents') !== false;
var showPatchHeaders = getStateByPage('show-patch-headers') !== false;
var showNotRelevant = getStateByPage('show-not-relevant') !== false;
setNotesColumns(notesWidth);
toggleTableOfContents(showTableOfContents);
togglePatchHeaders(showPatchHeaders);
toggleNotRelevant(showNotRelevant);
$('#patchNoteOptions').html(
'<div><label><input ' + (showTableOfContents ? 'checked ' : '') + 'id="show-table-of-contents" type="checkbox" /> Show Table of Contents?<label><br/>' +
'<label><input ' + (showPatchHeaders ? 'checked ' : '') + 'id="show-patch-headers" type="checkbox"/> Show patch headers in Table of Contents?<label><br/>'+
'<label><input ' + (showNotRelevant ? 'checked ' : '') + 'id="show-not-relevant" type="checkbox"/> Show content not marked as relevant to P99?<label></div>' +
'<div><label>Limit notes to a width of <input id="notes-width" placeholder="40" style="width: 4em;" value="' + notesWidth +'" /> columns (for readability)</label></div>'
);
$('#notes-width').change(function(e) {
var cols = parseFloat($(e.target).val());
setNotesColumns(cols);
setStateByPage('notes-width', cols);
});
$('#show-table-of-contents').change(function(e) {
var isChecked = $(e.target).is(':checked');
toggleTableOfContents(isChecked);
setStateByPage('show-table-of-contents', isChecked);
});
$('#show-patch-headers').change(function(e) {
var isChecked = $(e.target).is(':checked');
togglePatchHeaders(isChecked);
setStateByPage('show-patch-headers', isChecked);
});
$('#show-not-relevant').change(function(e) {
var isChecked = $(e.target).is(':checked');
toggleNotRelevant(isChecked);
setStateByPage('show-not-relevant', isChecked);
});
break;
}
// Warn users who accidentally try to edit a templated section
if ((window.location + '').includes('title=Template:Namedmobpage&action=edit')) {
alert('Warning: You are attempting you edit the template for all named mobs. You probably didn\'t mean to do that: you probably clicked on an edit link somewhere in the page and wound up here. To avoid this simply go back and use the edit *tab* at the top of the page instead.');
}
// Warn uses who try to edit a mostly-transcluded section (and offer to take them to the transcluded page)
var text = $('#wpTextbox1').val();
var match = text && text.match(/\{\{\#lsth\:(.*?)\|\[\[(.*?)\]\](.*)\}\}/);
if (match) {
var pageName = match[1];
var section = match[2];
var extra = match[3] || '';
var isEdit = (window.location + '').includes('action=edit');
var isUnderTenLines = $('#wpTextbox1').val().split('\n').length < 10;
var url = '/' + pageName + '#' + (section + extra).replace(/ /g, '_');
var message = 'This page uses "transclusion" to show part of another page, specifically the code:\n\n {{#lsth:' + pageName +
'|[[' + section + ']]' + extra + '}}\n\nIf you want to edit the transcluded section, click "Ok": you will be taken to that page.' +
' If you want to stay on this page, click "Cancel".';
if (isEdit && isUnderTenLines && confirm(message)) location = url;
}
// *** AUCTION TRACKER RELATED ***
var selectedServer = getGlobalState('selectedServer') || 'Blue';
var buildTabHtml = function(serverNames) {
var tabDivs = serverNames.map(function(name, i) {
return '<div id="' + name + 'Tab" class="tab' + (name === selectedServer ? ' selected' : '') + '">'+ name + '</div>';
});
return '<div class="tabs">' + tabDivs.join('') + '<div class="clear"></div></div>';
};
var selectTab = function(name) {
// show the server's box (and hide the others)
$trackers.hide();
var $tracker = $('#auc_' + name).show();
// If the selected tab doesn't exist on this item, show the first tab instead
if (!$tracker.length) $tracker = $('.auctrackerbox:first').show();
// Select the tab for that server (and unselect the others)
$('.auctrackerbox .tab').removeClass('selected');
var $tab = $('.auctrackerbox .tab:contains("' + name + '")');
if (!$tab.length) $tab = $('.auctrackerbox .tab:first');
$tab.addClass('selected');
setGlobalState('selectedServer', name);
};
var $trackers = $('.auctrackerbox');
// if we're on an item page with an auction tracker
if ($trackers.length) {
// Convert IDs of "auc_Blue" into an array of ["Blue", "Green", ...]
var servers = $trackers.toArray().map(function(tracker) {
return tracker.id.substr(4);
});
$trackers.prepend(buildTabHtml(servers));
selectTab(selectedServer);
$trackers.on('click', '.tab', function(e) {
selectTab($(e.target).text());
});
// Add links to search the forum for items to their auction tracker
// Forum IDs come from forum URLs, eg. red's auction forum is:
// https://www.project1999.com/forums/forumdisplay.php?f=59
// so we have "red: 59 " below
var forumIds = { blue: 27, green: 77, red: 59, teal: 78 };
$('.auctrackerbox span span:contains("Project 1999 Auction Tracker")').each(function(i, el) {
var $el = $(el);
var serverName = $el.closest('.auctrackerbox').attr('id').substr(4).toLowerCase();
const forumSearchUrl = 'https://www.project1999.com/forums/search.php?do=process&forumchoice[]=' +
forumIds[serverName] + '&query=%22' + $('#firstHeading').text() + '%22';
$el.append(
'<a ' +
'style="font-size: 0.5em; float: right" '+
'target="_new" ' +
'href="' + forumSearchUrl + '"' +
'>Search Forum</a>');
});
}
});