MediaWiki:Gadget-GalleryDetails.js
Jump to navigation
Jump to search
Note: After publishing, 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 / Edge: Hold Ctrl while clicking Refresh, or press Ctrl-F5
- Opera: Press Ctrl-F5.
// <source lang="javascript">
/*
Gallery details - reformat galleries to have one image below the next, and display extended image
information next to them. Works also on categories and Special:NewFiles. On Special:NewFiles, it
runs automatically unless you define
var gallery_details_newfiles_run = false;
in your monobook.js or other skin-specific JS file.
Original version written by Magnus Manske, with some partial fixes by others.
License of original: unknown.
Complete rewrite January 2009 by User:Lupo.
Author: [[User:Lupo]], January 2009
License: Quadruple licensed GFDL, GPL, LGPL and Creative Commons Attribution 3.0 (CC-BY-3.0)
*/
if (typeof (GalleryDetails) == 'undefined') { // Guard against double imports
importScript ('MediaWiki:Utilities.js'); // Generally useful operations
importScript ('MediaWiki:ImageLinks.js'); // Useful img links (Tineye search, del links for admins)
if (typeof (gallery_details_newfiles_run) == 'undefined')
var gallery_details_newfiles_run = true;
if (typeof (gallery_details_close_windows) == 'undefined')
var gallery_details_close_windows = false;
var gallery_details_good_tags = [
"GFDL",
"CC-",
"Cc-",
"PD",
"Pd",
"Public domain",
"Copyrighted free use",
"Attribution",
"Images requiring attribution",
"FAL",
"UK Government images",
"User-created GFDL images",
"Items with OTRS permission confirmed",
"GPL",
"LGPL"
];
var gallery_details_action_tags = [
"Flickr review needed",
"Flickr images needing",
"Recent unfree Flickr images"
];
var gallery_details_bad_tags = [
"Copyright violations",
"Images without ",
"Media without ",
"Media missing ",
"Unknown as of ",
"Deletion requests",
"Other speedy deletions",
"Possibly unfree"
];
var gallery_details_sidebar =
{ text : 'Gallery details'
,tip : 'Display info on images'
};
var gallery_details_nom_buttons = [{
label:'Deletion\xa0request...',
tip: 'Nominate the file for deletion and notify uploader',
del:true
}, {
label: 'Copyvio...',
tip: 'Mark as copyvio (prompting for a reason) and notify uploader',
tag: '{{copyvio|1=%PARAMETER%}}',
talk_tag: '{{subst:copyvionote|1=%FILE%}}',
img_summary: 'Marking as possible copyvio because %PARAMETER%',
talk_summary: 'Notification of possible copyright violation',
prompt_text: "Why is this file a copyright violation?"
}, {
label: 'No\xa0source',
tip : 'Mark as missing source info and notify uploader',
tag: '{{subst:nsd}}',
talk_tag: '{{subst:image source|1=%FILE%}}',
img_summary: 'File has no source',
talk_summary: '%FILE% does not have a source'
}, {
label: 'No\xa0permission',
tip : 'Mark as missing permission and notify uploader',
tag: '{{subst:npd}}',
talk_tag: '{{subst:image permission|1=%FILE%}}',
img_summary: 'Missing permission',
talk_summary: 'Please send permission for %FILE% to [[COM:OTRS|OTRS]]'
}, {
label: 'No\xa0license',
tip : 'Mark as missing license info and notify uploader',
tag: '{{subst:nld}}',
talk_tag: '{{subst:image license|1=%FILE%}}',
img_summary: 'Missing license',
talk_summary: '%FILE% does not have a license'
}];
// titleFromLink
// Extract a page title from a href of a link node. Works for both types of hrefs:
// https://foo.wikipedia.org/w/index.php?title=PageName and also /wiki/PageName
//
// Parameters
// node DOM node The link node from which the page name is to be extracted
function titleFromLink (node)
{
if (!node || typeof (node.getAttribute) != 'function') return "";
return titleFromHref (node.getAttribute ('href', 2));
// The ", 2" is for IE. IE sometimes has problems with encoded UTF-8 characters: using any other
// way to get the href, it insists to decode the value, but does do so wrongly. For more info,
// see https://commons.wikimedia.org/wiki/MediaWiki_talk:Gadget-HotCat.js/Archive01#Questions
}
// Localization hook. Check [[MediaWiki:Gadget-GalleryDetails.js/de]] for an example.
if (mw.config.get('wgUserLanguage') != 'en') importScript ('MediaWiki:Gadget-GalleryDetails.js/' + mw.config.get('wgUserLanguage'));
var GalleryDetailsViewer = function () {};
GalleryDetailsViewer.prototype =
{
display : function (model) // Redefine this in children
{
},
toggle : function (model) // Redefine this in children
{
},
// Default implementations
check_info : function (info)
{
if (!info.done)
return document.createTextNode ('Request failed.');
else if (!info.page || typeof (info.page.missing) != 'undefined')
return document.createTextNode ('File not found?!');
return null;
},
get_exif_data : function (info, keys)
{
if (!info || !info.page || !info.page.imageinfo) return null;
if (!keys) keys = ['Model', 'Make', 'DateTime', 'DateTimeOriginal'];
function find_metadata (list, keys)
{
if (!list || list.length == 0) return null;
var found = 0;
var result = {};
var all = !keys || keys.length == 0;
for (var i = 0; i < list.length && (all || found < keys.length); i++) {
if (all) {
result[list[i].name] = list[i].value;
found++;
} else {
for (var j = 0; j < keys.length; j++) {
if (list[i].name == keys[j]) {
result[list[i].name] = list[i].value;
found++;
break;
}
}
}
}
if (found == 0) return null; else return result;
}
var imagedata = info.page.imageinfo[0];
var result = [];
var exif = find_metadata (imagedata.metadata, keys);
var span = null;
if (exif) {
if (exif['Model']) {
if (exif['Make'] && exif['Model'].indexOf (exif['Make']) >= 0) exif['Make'] = null;
span = document.createElement ('span');
span.appendChild (document.createTextNode ('Camera: '));
if (exif['Make']) span.appendChild (document.createTextNode (exif['Make'] + ' '));
var a = makeRawLink (
exif['Model']
, 'https://en.wikipedia.org/wiki/' + encodeURI (exif['Model'])
);
a.className = 'external';
a.style.background = 'none';
a.style.padding = '0';
span.appendChild (a);
result[result.length] = span;
}
var time = exif['DateTime'] || exif['DateTimeOriginal'] || null;
if (time) {
span = document.createElement ('span');
span.appendChild (document.createTextNode ('EXIF time: ' + time));
result[result.length] = span;
}
}
return result;
},
create_details_box : function (info)
{
var page = info.page;
var title = info.name;
var imagedata = page.imageinfo[0];
var users = info.users;
var size = imagedata.size;
var width = imagedata.width;
var height = imagedata.height;
var url = imagedata.url;
var comment = imagedata.comment;
var timestamp = imagedata.timestamp;
// Output generation: image info
var t = document.createElement ('span');
t.appendChild (document.createTextNode (width + "×" + height + "px"));
if (width < 600 && height < 600 && width > 0 && height > 0) t.style.color = 'red';
var ndiv = document.createElement ('div');
ndiv.className = 'gallery_details_box';
ndiv.style.border = '3px solid '
+ (info.status == GalleryDetails.BAD_FILE
? 'red'
: (info.status == GalleryDetails.GOOD_FILE ? 'green' : 'yellow')
);
ndiv.style.margin = "5px";
ndiv.style.padding = "5px";
ndiv.appendChild (this.make_wiki_link (page.title));
ndiv.appendChild (document.createTextNode (' ('));
ndiv.appendChild (
makeRawLink (
'edit'
, mw.config.get('wgArticlePath').replace ('$1', encodeURI (page.title) + '?action=edit')
)
);
ndiv.appendChild (document.createTextNode (', '));
ndiv.appendChild (
makeRawLink (
'hist'
, mw.config.get('wgArticlePath').replace ('$1', encodeURI (page.title) + '?action=history')
)
);
ndiv.appendChild (document.createTextNode (')'));
ndiv.appendChild (document.createElement ('br'));
if (timestamp) {
timestamp = timestamp.replace ('T', '\xa0').replace ('Z', '\xa0(UTC)');
ndiv.appendChild (document.createTextNode (timestamp));
ndiv.appendChild (document.createElement ('br'));
}
ndiv.appendChild (t);
if (page.imageinfo.length > 1) {
t = document.createElement ('b');
t.appendChild (document.createTextNode (' (Re-upload)'));
ndiv.appendChild (t);
}
ndiv.appendChild (document.createElement ('br'));
if (imagedata.metadata) {
var exif = this.get_exif_data (info);
if (exif && exif.length > 0) {
for (var i = 0; i < exif.length; i++) {
ndiv.appendChild (exif[i]);
ndiv.appendChild (document.createElement ('br'));
}
}
}
ndiv.appendChild (this.make_wiki_link ('File_talk:' + title));
ndiv.appendChild (document.createElement ('br'));
var user = this.create_user_link (ndiv, users[0]);
if ((user == 'Rotatebot' || user == 'FlickreviewR' || user == 'Cropbot' || user == 'Picasa Review Bot') && users.length > 1) {
ndiv.appendChild (document.createElement ('br'));
t = document.createElement ('b');
t.appendChild (document.createTextNode ('Real: '));
ndiv.appendChild (t);
user = this.create_user_link (ndiv, users[1]);
}
if (info.categories && info.categories.length > 0) {
ndiv.appendChild (document.createElement ('hr'));
for (var i = 0; i < info.categories.length; i++) {
ndiv.appendChild (this.make_wiki_link (info.categories[i]));
if (i+1 < info.categories.length) ndiv.appendChild (document.createElement ('br'));
}
}
var text = page.revisions;
if (text) text = text[0];
this.create_action_links (ndiv, page.title, user, text ? text.revid : null, url);
return ndiv;
},
create_user_link : function (box, usernames)
{
var user = usernames.user;
var proxy = null;
if (usernames.real) {
proxy = user; user = usernames.real;
}
box.appendChild (this.make_wiki_link ('User:' + user));
box.appendChild (document.createTextNode (' ('));
box.appendChild (this.make_wiki_link ('User_talk:' + user, 'talk'));
box.appendChild (document.createTextNode (', '));
box.appendChild (
makeRawLink (
'logs'
, mw.config.get('wgArticlePath').replace ('$1', 'Special:Log') + '?user=' + encodeURIComponent (user)
)
);
box.appendChild (document.createTextNode (')'));
if (proxy) {
box.appendChild (document.createTextNode (' via\xa0'));
box.appendChild (this.make_wiki_link ('User:' + proxy, proxy));
box.appendChild (document.createTextNode (' ('));
box.appendChild (
makeRawLink (
'logs'
, mw.config.get('wgArticlePath').replace ('$1', 'Special:Log') + '?user='
+ encodeURIComponent (proxy)
)
);
box.appendChild (document.createTextNode (')'));
}
return user;
},
create_page_box : function (info)
{
var text = info.page.revisions[0];
if (!text) return null;
// Output generation: image page text
text = text["*"];
if (!text) return document.createTextNode ('\xa0');
var ndiv = document.createElement ('div');
ndiv.className = 'gallery_details_page_box';
ndiv.style.margin = "5px";
ndiv.style.padding = "5px";
ndiv.style.fontSize = "8pt";
ndiv.style.lineHeight = "9pt";
text = text.split('\n');
for (var i = 0; i < text.length; i++) {
var s = text[i];
var url_re = /^(.*?)(https?:\/\/[^ \]\}"\|<]*)(.*)$/; // " Fix syntax coloring
while (s.length > 0) {
var matches = url_re.exec (s);
if (matches && matches.length > 0) {
if (matches[1].length > 0)
ndiv.appendChild (document.createTextNode (matches[1]));
var a = makeRawLink (matches[2], matches[2]);
a.className = 'external';
a.style.background = 'none';
a.style.padding = '0';
ndiv.appendChild (a);
s = matches[3];
} else {
ndiv.appendChild (document.createTextNode (s));
break;
}
}
if (i + 1 < text.length) ndiv.appendChild (document.createElement ('br'));
}
return ndiv;
},
create_action_links : function (ndiv, title, user, rev_id, img_url)
{
var tools = $('<div style="font-size: small; background: #DDD;"></div>');
$.each(gallery_details_nom_buttons, function (k, v) {
var link = $('<a href="#" title="' + v.tip + '">'+v.label+'</a>');
if (v.del) {
link.click(function(event) {
event.preventDefault();
AjaxQuickDelete.nominateForDeletion(title);
});
} else {
link.click(function(event) {
event.preventDefault();
AjaxQuickDelete.insertTagOnPage(v.tag, v.img_summary, v.talk_tag, v.talk_summary, v.prompt_text, title);
});
}
if (k>0) tools.append('\xa0| ');
tools.append(link);
});
tools = tools.get(0);
var additional_links = ImageLinks.get_links (title, user, rev_id, img_url);
// If we have additional links, those from the first group may be added for anyone.
if (additional_links && additional_links.length > 0) {
if (additional_links[0] && additional_links[0].length > 0) {
for (var i = 0; i < additional_links[0].length; i++) {
tools.appendChild (document.createTextNode ('\xa0| '));
tools.appendChild (additional_links[0][i]);
}
}
if (mw.config.get('wgUserGroups').join (' ').indexOf ('sysop') >= 0 && additional_links.length > 1) {
tools.appendChild (document.createElement ('hr'));
tools.appendChild (document.createTextNode ('Quick deletions (without user notification)'));
tools.appendChild (document.createElement ('br'));
for (var i = 1; i < additional_links.length; i++) {
if (additional_links[i]) {
for (var j = 0; j < additional_links[i].length; j++) {
if (j > 0) tools.appendChild (document.createTextNode ('\xa0| '));
tools.appendChild (additional_links[i][j]);
}
if (i+1 < additional_links.length) tools.appendChild (document.createElement ('br'));
}
}
}
}
ndiv.appendChild (tools);
},
make_wiki_link : function (title, text)
{
if (!text) text = title.replace (/_/g, ' ');
var result =
makeRawLink (
text
, mw.config.get('wgArticlePath').replace ('$1', encodeURI (title.replace (/ /g, '_')))
, null
, text);
return result;
}
};
var GalleryDetailsTableViewer = function () {};
GalleryDetailsTableViewer.prototype = new GalleryDetailsViewer;
GalleryDetailsTableViewer.prototype.display =
function (model)
{
// Display the images in the model in a new table, one image per row.
this.view = document.createElement ('table');
this.view.className = 'gallery_details';
this.view.style.display = 'none';
model.root.parentNode.insertBefore (this.view, model.root);
for (var i = 0; i < model.nof_images; i++) {
var existing = model.image_list[i];
if (!existing.box.parentNode) continue; // This image is no longer in the table?!
var row = this.view.insertRow (-1);
var cell = null;
if (existing.box.nodeName.toLowerCase () == 'table') {
cell = document.createElement ('td');
cell.appendChild (existing.box.cloneNode (true));
cell.colSpan = "2";
row.appendChild (cell);
row = this.view.insertRow (-1);
} else if (existing.box.nodeName.toLowerCase () == 'li') { // MW1.17
cell = document.createElement('td');
var toCopy = existing.box.firstChild;
while (toCopy && toCopy.nodeType != 1) toCopy = toCopy.nextSibling;
if (toCopy) {
cell.appendChild (toCopy.cloneNode (true));
row.appendChild (cell);
}
} else { // pre MW1.17 gallery; existing.box.parentNode is a table cell
cell = existing.box.parentNode.cloneNode (true);
row.appendChild (cell);
}
cell = document.createElement ('td');
var details = this.check_info (existing);
var page_content = null;
if (!details) {
details = this.create_details_box (existing);
page_content = this.create_page_box (existing) || document.createTextNode ('No info found.');
}
if (!page_content) cell.colSpan = "2";
cell.appendChild (details);
row.appendChild (cell);
if (page_content) {
cell = document.createElement ('td');
cell.appendChild (page_content);
row.appendChild (cell);
}
}
this.toggle (model);
};
GalleryDetailsTableViewer.prototype.toggle =
function (model)
{
x = model.root.style.display;
model.root.style.display = this.view.style.display;
this.view.style.display = x;
};
var GalleryDetails = function () {this.initialize.apply (this, arguments);};
GalleryDetails.ACTION_NEEDED = 0;
GalleryDetails.GOOD_FILE = 1;
GalleryDetails.BAD_FILE = 2;
GalleryDetails.prototype =
{
root : null,
image_list : [],
wrapper : null,
nof_images : 0,
handled : -1,
viewer : null,
injectSpinner: function (elementBefore, id) {
// Will be replaced once jQuery.spinner module is loaded
},
removeSpinner: function (id) {
// Will be replaced once jQuery.spinner module is loaded
},
initialize : function (root, id, is_single)
{
this.is_single = is_single;
this.root = root;
this.wrapper = document.createElement ('div');
this.wrapper.id = id;
var spinner_anchor = document.createElement ('span');
this.wrapper.appendChild (spinner_anchor);
this.root.parentNode.insertBefore (this.wrapper, this.root);
var existing = null;
if (is_single)
existing = window.jQuery(this.root).find('.gallerybox');
else
existing = window.jQuery(this.root).find('table.searchResultImage');
if (!existing || existing.length == 0) return;
// Extract the names
this.image_list = new Array ();
for (var i = 0; i < existing.length; i++) {
var this_title = this.title_from_box (existing[i]);
if (this_title && this_title.length > 0) {
this.image_list[this.image_list.length] =
{ name : this_title.replace (/ /g, '_')
, box : existing[i]
, done : false
, page : null
, categories : null
, status : GalleryDetails.ACTION_NEEDED
, table : existing[i]
, users : null
};
} else {
var errorbox = window.jQuery(existing[i]).find('table.MediaTransformError');
if (errorbox && errorbox.length > 0) {
errorbox[0].style.width = errorbox[0].parentNode.offsetWidth + 'px';
errorbox[0].style.height = "";
}
}
}
this.nof_images = this.image_list.length;
if (this.nof_images == 0) return;
this.handled = 0;
// Now start the query (or queries). We limit this to at most 50 filenames per request to avoid
// hitting a server limit.
var start = 0;
var to_do = this.nof_images;
this.injectSpinner (spinner_anchor, id);
while (to_do > 0) {
var chunk = 50;
if (chunk > to_do) chunk = to_do;
this.make_call (start, chunk);
to_do = to_do - chunk;
start = start + chunk;
}
},
make_call : function (from, length)
{
// Get the filenames of images #from to #(from + length - 1)
var titles = "";
for (var idx = from; idx < from + length; idx++) {
if (this.image_list[idx].name && this.image_list[idx].name.length > 0) {
titles += (titles.length > 0 ? '|' : "")
+ 'File:' + encodeURIComponent (this.image_list[idx].name);
}
}
var this_obj = this;
$.ajax({
url: mw.config.get('wgServer') + mw.config.get('wgScriptPath') + '/api.php'
,type: 'POST' // Avoid Get-request URL length limits
,data: 'format=json&action=query&prop=imageinfo|categories|revisions&iiprop=timestamp|user|comment|url|size|metadata'
+ '&rvdir=older&rvprop=ids|content&iilimit=2&cllimit=' + length * 10 + '&titles=' + titles
,dataType: 'json'
,success: function (json) { this_obj.add_info (json, from, length); }
,error: function () { this_obj.done (length); }
});
},
add_info : function (info, from, length)
{
if (info) {
for (var i = from; i < from + length; i++) {
this.image_list[i].done = true;
var title = this.image_list[i].name; // No namespace prefix!
if (!title || title.length == 0) continue;
// Search through the results to find this entry
var page = null;
for (var p in info.query.pages) {
// Rm namespace for comparison
info.query.pages[p].title = info.query.pages[p].title.replace (/ /g, '_');
var colon = info.query.pages[p].title.indexOf (':');
if (title == info.query.pages[p].title.substr (colon + 1)) {
page = info.query.pages[p]; break;
}
}
if (page) {
this.image_list[i].page = page;
// Category check
if (typeof (page.missing) == 'undefined') {
var catdata = page.categories;
var categories = new Array();
var goodcat = false;
var badcat = false;
var actioncat = false;
if (catdata) {
for (var cidx = 0 ; cidx < catdata.length ; cidx++) {
var cat = catdata[cidx].title;
goodcat = goodcat || this.cat_match (cat, gallery_details_good_tags);
badcat = badcat || this.cat_match (cat, gallery_details_bad_tags);
actioncat = actioncat || this.cat_match (cat, gallery_details_action_tags);
categories[categories.length] = cat;
}
}
if (actioncat) goodcat = false;
this.image_list[i].categories = categories;
this.image_list[i].status =
(badcat ? GalleryDetails.BAD_FILE
: (goodcat ? GalleryDetails.GOOD_FILE : GalleryDetails.ACTION_NEEDED)
);
// Try to handle bot uploads
if (page.imageinfo && page.imageinfo.length > 0) {
this.image_list[i].users = new Array ();
this.image_list[i].users[0] = {user : page.imageinfo[0].user, real : null};
if (page.imageinfo.length > 1)
this.image_list[i].users[1] = {user : page.imageinfo[1].user, real : null};
} else
this.image_list[i].page = null;
if ( page.imageinfo && page.imageinfo.length > 0
&& page.revisions && page.revisions.length > 0) {
var text = page.revisions[0];
if (text) text = text["*"];
if (text) {
for (var u = 0; u < this.image_list[i].users.length; u++) {
var match = null;
var user = this.image_list[i].users[u].user;
if (user.replace (/ /g, '_') == 'Flickr_upload_bot') {
// Check for the bot's upload template
match =
/\{\{User:Flickr upload bot\/upload(\|[^\|\}]*)?\|reviewer=([^\}]*)\}\}/.exec (text);
if (match) match = match[2];
} else if (user == 'File Upload Bot (Magnus Manske)') {
// CommonsHelper
match =
/transferred to Commons by \[\[User:([^\]\|]*)(\|([^\]]*))?\]\] using/.exec (text);
if (!match)
// geograph_org2commons, regex accounts for typo ("transferd") and its
// possible future correction
match =
/geograph.org.uk\]; transferr?e?d by \[\[User:([^\]\|]*)(\|([^\]]*))?\]\] using/.exec (text);
if (!match && /(www\.)?flickr\.com\/photos\//.test (text))
// flickr2commons
match = /\* Uploaded by \[\[User:([^\]\|]*)(\|([^\]]*))?\]\]/.exec (text);
if (match) match = match[1];
function fix_double_encoding (match) {
if (!match) return match;
var utf8 = /[\u00C2-\u00F4][\u0080-\u00BF][\u0080-\u00BF]?[\u0080-\u00BF]?/g;
if (!utf8.test (match)) return match;
// Looks like we have a double encoding. At least it contains character
// sequences that might be legal UTF-8 encodings. Translate them into %-
// syntax and try to decode again.
var temp = "", curr = 0, m, hex_digit = "0123456789ABCDEF";
var str = match.replace (/%/g, '%25');
utf8.lastIndex = 0; // Reset regexp to beginning of string
try {
while ((m = utf8.exec (str)) != null) {
temp += str.substring (curr, m.index);
m = m[0];
for (var i = 0; i < m.length; i++) {
temp += '%'
+ hex_digit.charAt (m.charCodeAt (i) / 16)
+ hex_digit.charAt (m.charCodeAt (i) % 16);
}
curr = utf8.lastIndex;
}
if (curr < str.length) temp += str.substring (curr);
temp = decodeURIComponent (temp);
return temp;
} catch (e) {
}
return match;
}
match = fix_double_encoding (match);
} else if (user == 'FlickrLickr') {
match = /\n\|reviewer=\s*(.*)\n/.exec (text);
if (match) match = match[1];
}
if (match)
this.image_list[i].users[u].real =
match.replace (/^\s\s*/, "").replace (/\s\s*$/, "");
}
}
}
}
}
} // end loop
}
this.done (length);
},
done : function (n)
{
this.handled += n;
if (this.handled >= this.nof_images) {
// Done; display it
this.removeSpinner (this.wrapper.id);
if (this.is_single) {
this.viewer = GalleryDetailsLoader.getViewer ();
this.viewer.display (this);
} else {
// Create viewers for each entry, and pass them a faked model
this.viewer = new Array ();
for (var i = 0; i < this.nof_images; i++) {
this.viewer[this.viewer.length] =
{ view : GalleryDetailsLoader.getViewer ()
,root : this.image_list[i].table
,image_list : [this.image_list[i]]
,nof_images : 1
,wrapper : this.wrapper
};
}
for (var i = 0; i < this.viewer.length; i++)
this.viewer[i].view.display (this.viewer[i]);
}
}
},
toggle : function ()
{
if (this.handled >= this.nof_images) {
if (this.is_single) {
this.viewer.toggle (this);
} else {
for (var i = 0; i < this.viewer.length; i++)
this.viewer[i].view.toggle (this.viewer[i]);
}
}
},
title_from_box : function (box)
{
var thumblks = window.jQuery(box).find('a.image');
if (thumblks && thumblks.length > 0 && thumblks[0]) {
// Extract the file name (without namespace) from the link
var name = titleFromLink (thumblks[0]) || "";
return name.substring (name.indexOf (':') + 1); // Strip namespace
}
return "";
},
cat_match : function (cat, test)
{
if (!cat) return false;
var c = cat.substr (cat.indexOf (':') + 1); // Strip namespace
for (var i = 0; i < test.length; i++ ) {
if (c.substr (0, test[i].length) == test[i]) return true;
}
return false;
}
}; // end GalleryDetails
mw.loader.using('jquery.spinner', function () {
GalleryDetails.prototype.injectSpinner = function (elementBefore, id) {
window.jQuery(elementBefore).injectSpinner(id);
};
GalleryDetails.prototype.removeSpinner = function (id) {
window.jQuery.removeSpinner(id);
};
});
window.GalleryDetailsLoader =
{
initialized : false,
initialize : function ()
{
GalleryDetailsLoader.initialized = true;
var tables = window.jQuery('.gallery');
if (tables.length == 0) {
// Check whether we're on Special:Search (or a modified Special:Log) and have image results
if (mw.config.get('wgNamespaceNumber') == -1)
tables = window.jQuery('table.searchResultImage');
}
if (tables.length == 0) return; // Nothing here: nothing to do.
if (gallery_details_newfiles_run
&& mw.config.get('wgNamespaceNumber') == -1 // Special
&& mw.config.get('wgCanonicalSpecialPageName') == "Newimages") {
GalleryDetailsLoader.autoStart ();
} else {
mw.util.addPortletLink(
'p-tb'
,'javascript:GalleryDetailsLoader.load ();'
,gallery_details_sidebar.text
,'t-gallerydetails'
,gallery_details_sidebar.tip
);
}
},
autoStart : function () {
if (typeof window.titleFromHref == 'undefined' || typeof window.ImageLinks == 'undefined') {
// Wait until we have our asynchronously loaded dependencies (importScript above)
window.setTimeout (GalleryDetailsLoader.autoStart, 500); // Half a second
return;
}
GalleryDetailsLoader.load ();
},
loaders : [],
load : function ()
{
if (GalleryDetailsLoader.loaders.length > 0) {
for (var i = 0; i < GalleryDetailsLoader.loaders.length; i++) {
GalleryDetailsLoader.loaders[i].toggle ();
}
} else {
var tables = window.jQuery('.gallery');
if (tables.length > 0) {
for (var i = 0; i < tables.length; i++) {
GalleryDetailsLoader.loaders[GalleryDetailsLoader.loaders.length] =
new GalleryDetails (
tables[i]
, 'gallery_details_wrapper_' + i
, true
)
;
}
} else if (mw.config.get('wgNamespaceNumber') == -1) {
tables = window.jQuery('table.searchResultImage');
if (tables.length > 0) {
var list = tables[0].parentNode;
if (list.nodeName.toLowerCase () == 'li')
list = list.parentNode;
else
return;
GalleryDetailsLoader.loaders[GalleryDetailsLoader.loaders.length] =
new GalleryDetails (
list
, 'gallery_details_wrapper_' + i
, false
)
;
}
}
}
},
getViewer : function ()
{
return new GalleryDetailsTableViewer ();
}
};
$(document).ready(GalleryDetailsLoader.initialize);
} // end if (guard against double imports)
// </source>