diff options
Diffstat (limited to 'skins/common')
-rw-r--r-- | skins/common/ajax.js | 21 | ||||
-rw-r--r-- | skins/common/ajaxwatch.js | 99 | ||||
-rw-r--r-- | skins/common/block.js | 16 | ||||
-rw-r--r-- | skins/common/cologneblue.css | 13 | ||||
-rw-r--r-- | skins/common/commonPrint.css | 3 | ||||
-rw-r--r-- | skins/common/common_rtl.css | 9 | ||||
-rw-r--r-- | skins/common/diff.css | 74 | ||||
-rw-r--r-- | skins/common/diff.js | 20 | ||||
-rw-r--r-- | skins/common/images/spinner.gif | bin | 0 -> 2285 bytes | |||
-rw-r--r-- | skins/common/oldshared.css | 465 | ||||
-rw-r--r-- | skins/common/protect.js | 172 | ||||
-rw-r--r-- | skins/common/shared.css | 48 | ||||
-rw-r--r-- | skins/common/upload.js | 175 | ||||
-rw-r--r-- | skins/common/wikibits.js | 292 |
14 files changed, 1175 insertions, 232 deletions
diff --git a/skins/common/ajax.js b/skins/common/ajax.js index d90bea09..854d7a00 100644 --- a/skins/common/ajax.js +++ b/skins/common/ajax.js @@ -39,16 +39,21 @@ function sajax_init_object() { sajax_debug("sajax_init_object() called..") var A; try { - A=new ActiveXObject("Msxml2.XMLHTTP"); + // Try the new style before ActiveX so we don't + // unnecessarily trigger warnings in IE 7 when + // set to prompt about ActiveX usage + A = new XMLHttpRequest(); } catch (e) { try { - A=new ActiveXObject("Microsoft.XMLHTTP"); - } catch (oc) { - A=null; + A=new ActiveXObject("Msxml2.XMLHTTP"); + } catch (e) { + try { + A=new ActiveXObject("Microsoft.XMLHTTP"); + } catch (oc) { + A=null; + } } } - if(!A && typeof XMLHttpRequest != "undefined") - A = new XMLHttpRequest(); if (!A) sajax_debug("Could not create connection object."); @@ -75,7 +80,9 @@ function sajax_do_call(func_name, args, target) { var i, x, n; var uri; var post_data; - uri = wgServer + wgScriptPath + "/index.php?action=ajax"; + uri = wgServer + + ((wgScript == null) ? (wgScriptPath + "/index.php") : wgScript) + + "?action=ajax"; if (sajax_request_type == "GET") { if (uri.indexOf("?") == -1) uri = uri + "?rs=" + encodeURIComponent(func_name); diff --git a/skins/common/ajaxwatch.js b/skins/common/ajaxwatch.js index 16e4fdc4..b30e4ffd 100644 --- a/skins/common/ajaxwatch.js +++ b/skins/common/ajaxwatch.js @@ -2,10 +2,10 @@ // * ajax.js: /*extern sajax_init_object, sajax_do_call */ // * wikibits.js: - /*extern changeText, akeytt, hookEvent */ + /*extern changeText, akeytt, hookEvent, jsMsg */ // These should have been initialized in the generated js -/*extern wgAjaxWatch, wgArticleId */ +/*extern wgAjaxWatch, wgPageName */ if(typeof wgAjaxWatch === "undefined" || !wgAjaxWatch) { var wgAjaxWatch = { @@ -20,32 +20,60 @@ wgAjaxWatch.supported = true; // supported on current page and by browser wgAjaxWatch.watching = false; // currently watching page wgAjaxWatch.inprogress = false; // ajax request in progress wgAjaxWatch.timeoutID = null; // see wgAjaxWatch.ajaxCall -wgAjaxWatch.watchLink1 = null; // "watch"/"unwatch" link -wgAjaxWatch.watchLink2 = null; // second one, for (some?) non-Monobook-based -wgAjaxWatch.oldHref = null; // url for action=watch/action=unwatch +wgAjaxWatch.watchLinks = []; // "watch"/"unwatch" links wgAjaxWatch.setLinkText = function(newText) { - changeText(wgAjaxWatch.watchLink1, newText); - if (wgAjaxWatch.watchLink2) { - changeText(wgAjaxWatch.watchLink2, newText); + for (i = 0; i < wgAjaxWatch.watchLinks.length; i++) { + changeText(wgAjaxWatch.watchLinks[i], newText); } }; wgAjaxWatch.setLinkID = function(newId) { - wgAjaxWatch.watchLink1.id = newId; + // We can only set the first one + wgAjaxWatch.watchLinks[0].setAttribute( 'id', newId ); akeytt(newId); // update tooltips for Monobook }; +wgAjaxWatch.setHref = function( string ) { + for( i = 0; i < wgAjaxWatch.watchLinks.length; i++ ) { + if( string == 'watch' ) { + wgAjaxWatch.watchLinks[i].href = wgAjaxWatch.watchLinks[i].href + .replace( /&action=unwatch/, '&action=watch' ); + } else if( string == 'unwatch' ) { + wgAjaxWatch.watchLinks[i].href = wgAjaxWatch.watchLinks[i].href + .replace( /&action=watch/, '&action=unwatch' ); + } + } +} + wgAjaxWatch.ajaxCall = function() { - if(!wgAjaxWatch.supported || wgAjaxWatch.inprogress) { - return; + if(!wgAjaxWatch.supported) { + return true; + } else if (wgAjaxWatch.inprogress) { + return false; } + if(!wfSupportsAjax()) { + // Lazy initialization so we don't toss up + // ActiveX warnings on initial page load + // for IE 6 users with security settings. + wgAjaxWatch.supported = false; + return true; + } + wgAjaxWatch.inprogress = true; - wgAjaxWatch.setLinkText(wgAjaxWatch.watching ? wgAjaxWatch.unwatchingMsg : wgAjaxWatch.watchingMsg); - sajax_do_call("wfAjaxWatch", [wgArticleId, (wgAjaxWatch.watching ? "u" : "w")], wgAjaxWatch.processResult); + wgAjaxWatch.setLinkText( wgAjaxWatch.watching + ? wgAjaxWatch.unwatchingMsg : wgAjaxWatch.watchingMsg); + sajax_do_call( + "wfAjaxWatch", + [wgPageName, (wgAjaxWatch.watching ? "u" : "w")], + wgAjaxWatch.processResult + ); // if the request isn't done in 10 seconds, allow user to try again - wgAjaxWatch.timeoutID = window.setTimeout(function() { wgAjaxWatch.inprogress = false; }, 10000); - return; + wgAjaxWatch.timeoutID = window.setTimeout( + function() { wgAjaxWatch.inprogress = false; }, + 10000 + ); + return false; }; wgAjaxWatch.processResult = function(request) { @@ -53,20 +81,22 @@ wgAjaxWatch.processResult = function(request) { return; } var response = request.responseText; - if(response == "<err#>") { - window.location.href = wgAjaxWatch.oldHref; - return; - } else if(response == "<w#>") { + if( response.match(/^<w#>/) ) { wgAjaxWatch.watching = true; wgAjaxWatch.setLinkText(wgAjaxWatch.unwatchMsg); wgAjaxWatch.setLinkID("ca-unwatch"); - wgAjaxWatch.oldHref = wgAjaxWatch.oldHref.replace(/action=watch/, "action=unwatch"); - } else if(response == "<u#>") { + wgAjaxWatch.setHref( 'unwatch' ); + } else if( response.match(/^<u#>/) ) { wgAjaxWatch.watching = false; wgAjaxWatch.setLinkText(wgAjaxWatch.watchMsg); wgAjaxWatch.setLinkID("ca-watch"); - wgAjaxWatch.oldHref = wgAjaxWatch.oldHref.replace(/action=unwatch/, "action=watch"); + wgAjaxWatch.setHref( 'watch' ); + } else { + // Either we got a <err#> error code or it just plain broke. + window.location.href = wgAjaxWatch.watchLinks[0].href; + return; } + jsMsg( response.substr(4), 'watch' ); wgAjaxWatch.inprogress = false; if(wgAjaxWatch.timeoutID) { window.clearTimeout(wgAjaxWatch.timeoutID); @@ -75,6 +105,8 @@ wgAjaxWatch.processResult = function(request) { }; wgAjaxWatch.onLoad = function() { + // This document structure hardcoding sucks. We should make a class and + // toss all this out the window. var el1 = document.getElementById("ca-unwatch"); var el2 = null; if (!el1) { @@ -96,20 +128,19 @@ wgAjaxWatch.onLoad = function() { } } - if(!wfSupportsAjax()) { - wgAjaxWatch.supported = false; - return; - } - // The id can be either for the parent (Monobook-based) or the element // itself (non-Monobook) - wgAjaxWatch.watchLink1 = el1.tagName.toLowerCase() == "a" ? el1 : el1.firstChild; - wgAjaxWatch.watchLink2 = el2 ? el2 : null; + wgAjaxWatch.watchLinks.push( el1.tagName.toLowerCase() == "a" + ? el1 : el1.firstChild ); - wgAjaxWatch.oldHref = wgAjaxWatch.watchLink1.getAttribute("href"); - wgAjaxWatch.watchLink1.setAttribute("href", "javascript:wgAjaxWatch.ajaxCall()"); - if (wgAjaxWatch.watchLink2) { - wgAjaxWatch.watchLink2.setAttribute("href", "javascript:wgAjaxWatch.ajaxCall()"); + if( el2 ) { + wgAjaxWatch.watchLinks.push( el2 ); + } + + // I couldn't get for (watchLink in wgAjaxWatch.watchLinks) to work, if + // you can be my guest. + for( i = 0; i < wgAjaxWatch.watchLinks.length; i++ ) { + wgAjaxWatch.watchLinks[i].onclick = wgAjaxWatch.ajaxCall; } return; }; @@ -124,4 +155,4 @@ function wfSupportsAjax() { var supportsAjax = request ? true : false; delete request; return supportsAjax; -}
\ No newline at end of file +} diff --git a/skins/common/block.js b/skins/common/block.js index c9c02446..430c1d54 100644 --- a/skins/common/block.js +++ b/skins/common/block.js @@ -22,26 +22,32 @@ function considerChangingExpiryFocus() { function updateBlockOptions() { if (!document.getElementById) return; - + var target = document.getElementById('mw-bi-target'); if (!target) return; - + var addy = target.value; var isEmpty = addy.match(/^\s*$/); var isIp = addy.match(/^(\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}|:(:[0-9A-Fa-f]{1,4}){1,7}|[0-9A-Fa-f]{1,4}(:{1,2}[0-9A-Fa-f]{1,4}|::$){1,7})(\/\d+)?$/); - + /* var anonymousCheck = document.getElementById('wpAnonOnly'); anonymousCheck.disabled = !isIp && !isEmpty; - + var autoblockCheck = document.getElementById('wpEnableAutoblock'); autoblockCheck.disabled = isIp && !isEmpty; + + var emailblockCheck = document.getElementById('wpEmailBan'); + emailblockCheck.disabled = isIp && !isEmpty; */ var anonymousRow = document.getElementById('wpAnonOnlyRow'); anonymousRow.style.display = (!isIp && !isEmpty) ? 'none' : ''; - + var autoblockRow = document.getElementById('wpEnableAutoblockRow'); autoblockRow.style.display = isIp && !isEmpty ? 'none' : ''; + + var emailblockRow = document.getElementById('wpEnableEmailBan'); + emailblockRow.style.display = isIp && !isEmpty ? 'none' : ''; } diff --git a/skins/common/cologneblue.css b/skins/common/cologneblue.css index 5b6e5bca..547585ef 100644 --- a/skins/common/cologneblue.css +++ b/skins/common/cologneblue.css @@ -93,4 +93,15 @@ a.stub, #quickbar a.stub { color:#772233; text-decoration:none; } a.new, #quickbar a.new { color: #CC2200; } h2, h3, h4, h5, h6 { margin-bottom: 0; } small { font-size: 75%; } -input.mw-searchInput { width: 106px; }
\ No newline at end of file +input.mw-searchInput { width: 106px; } + +/* Recreating-deleted-page warning and log entries */ +div#mw-recreate-deleted-warn { + padding: 3px; + margin-top: 3px; + margin-bottom: 3px; + border: 1px solid #6688AA; +} +div#mw-recreate-deleted-warn ul li { + font-size: 90%; +}
\ No newline at end of file diff --git a/skins/common/commonPrint.css b/skins/common/commonPrint.css index 4fddafaa..a7d49e36 100644 --- a/skins/common/commonPrint.css +++ b/skins/common/commonPrint.css @@ -73,6 +73,9 @@ div.tleft { margin-right:0.5em; border-width: 0.5em 1.4em 0.8em 0; } +img.thumbborder { + border: 1px solid #dddddd; +} /* table standards */ table.rimage { diff --git a/skins/common/common_rtl.css b/skins/common/common_rtl.css index 0c08de55..d26acc13 100644 --- a/skins/common/common_rtl.css +++ b/skins/common/common_rtl.css @@ -1,5 +1,7 @@ -/* This CSS file is called from absolutely every wiki that's RTL: unlike - * common.css, it's actually common to all skins. */ +/* + * This file contains CSS settings common to RTL wikis use the old + * pre-Monobook skins Wikistandard, Nostalgia and CologneBlue + */ /* js pref toc */ #preftoc { float: right; } @@ -30,3 +32,6 @@ div.tleft, div.floatleft { p.mw-ipb-conveniencelinks { float: left; } +table.filehistory th { + text-align: right; +} diff --git a/skins/common/diff.css b/skins/common/diff.css new file mode 100644 index 00000000..6a1f23b5 --- /dev/null +++ b/skins/common/diff.css @@ -0,0 +1,74 @@ +/* +** Diff rendering +*/ +table.diff, td.diff-otitle, td.diff-ntitle { + background-color: white; +} +td.diff-otitle, +td.diff-ntitle { + text-align: center; +} +td.diff-marker { + text-align: right; +} +.rtl td.diff-marker { + text-align: left; +} +td.diff-lineno { + font-weight: bold; +} +td.diff-addedline { + background: #cfc; + font-size: smaller; +} +td.diff-deletedline { + background: #ffa; + font-size: smaller; +} +td.diff-context { + background: #eee; + font-size: smaller; +} +.diffchange { + color: red; + font-weight: bold; + text-decoration: none; +} + +table.diff { + border: none; + width: 98%; + border-spacing: 4px; + + /* Fixed layout is required to ensure that cells containing long URLs + don't widen in Safari, Internet Explorer, or iCab */ + table-layout: fixed; +} +table.diff td { + padding: 0; +} +table.diff col.diff-marker { + width: 2%; +} +table.diff col.diff-content { + width: 48%; +} +table.diff td div { + /* Force-wrap very long lines such as URLs or page-widening char strings. + CSS 3 draft..., but Gecko doesn't support it yet: + https://bugzilla.mozilla.org/show_bug.cgi?id=99457 */ + word-wrap: break-word; + + /* As fallback, scrollbars will be added for very wide cells + instead of text overflowing or widening */ + overflow: auto; + + /* The above rule breaks on very old versions of Mozilla due + to a bug which collapses the table cells to a single line. + + In Mozilla 1.1 and below with JavaScript enabled, the rule + will be overridden with this by diff.js; wide cell contents + then spill horizontally without widening the rest of the + table: */ + /* overflow: visible; */ +} diff --git a/skins/common/diff.js b/skins/common/diff.js new file mode 100644 index 00000000..e80a895c --- /dev/null +++ b/skins/common/diff.js @@ -0,0 +1,20 @@ +/* +Workaround for overflow bug in Mozilla 1.1 and earlier, where scrolling +<div>s in <td> cells collapse their height to a single line. + +Known to be fixed in 1.2.1 (Gecko 20021130), but the CSS hacks I've tried +with overflow-x disable the scrolling all the way until Mozilla 1.8 / FF 1.5 +and break Opera as well. + +So... we check for reaaaally old Gecko and hack in an alternate rule to let +the wide cells spill instead of scrolling them. Not ideal as it won't work +if JS is disabled, of course. +*/ + +if (navigator && navigator.product == "Gecko" && navigator.productSub < "20021130") { + var sheets = document.styleSheets; + var lastSheet = sheets[sheets.length-1]; + lastSheet.insertRule( + "table.diff td div { overflow: visible; }", + lastSheet.cssRules.length); +}
\ No newline at end of file diff --git a/skins/common/images/spinner.gif b/skins/common/images/spinner.gif Binary files differnew file mode 100644 index 00000000..57d749b0 --- /dev/null +++ b/skins/common/images/spinner.gif diff --git a/skins/common/oldshared.css b/skins/common/oldshared.css new file mode 100644 index 00000000..27d93a03 --- /dev/null +++ b/skins/common/oldshared.css @@ -0,0 +1,465 @@ +/* + * oldshared.css + * This file contains CSS settings common to Wikistandard, Nostalgia and + * CologneBlue, the old pre-Monobook skins + */ + +/* For clarity, explicitly state some recommendations from <http://www.w3.org/ + TR/CSS21/sample.html> to make sure the editsection links scale right */ + +h1 { font-size: 2em; } +h2 { font-size: 1.5em; } +h3 { font-size: 1.17em; } +h5 { font-size: .83em; } +h6 { font-size: .75em; } +h1, h2, h3, h4, h5, h6 { font-weight: bolder } + +/* Now the custom parts */ + +/* Make edit sections (which are inside h# tags) normal-sized */ +.editsection { + font-weight: normal; +} +h1 .editsection { font-size: 50% } +h2 .editsection { font-size: 66.7% } +h3 .editsection { font-size: 85.5% } +h5 .editsection { font-size: 120% } +h6 .editsection { font-size: 133% } + +#footer { clear: both } +/* images */ +div.floatright { float: right; clear: right; margin: 0 0 1em 1em; } +div.floatright p { font-style: italic; } +div.floatleft { float: left; clear: left; margin: 0.3em 0.5em 0.5em 0; } +div.floatleft p { font-style: italic; } + + +/* Print-specific things to hide */ +.printfooter { + display: none; +} + +/* table standards */ +table.rimage { + float:right; + margin-left:1em; + margin-bottom:1em; + text-align:center; + font-size:smaller; +} + +/* thumbnails */ +div.thumb { + margin-bottom: .5em; + border-style: solid; + border-color: white; + width: auto; +} +div.thumbinner { + border: 1px solid #ccc; + padding: 3px !important; + background-color: #f9f9f9; + font-size: 94%; + text-align: center; + overflow: hidden; +} +html .thumbimage { + border: 1px solid #ccc; +} +html .thumbcaption { + border: none; + text-align: left; + line-height: 1.4em; + padding: 3px !important; + font-size: 94%; +} +div.magnify { + float: right; + border: none !important; + background: none !important; +} +div.magnify a, div.magnify img { + display: block; + border: none !important; + background: none !important; +} +div.tright { + clear: right; + float: right; + border-width: .5em 0 .8em 1.4em; +} +div.tleft { + float: left; + clear: left; + margin-right: .5em; + border-width: .5em 1.4em .8em 0; +} +img.thumbborder { + border: 1px solid #dddddd; +} + +/* Page history styling */ +/* the auto-generated edit comments */ +.autocomment { color: #4b4b4b; } +#pagehistory span.user { + margin-left: 1.4em; + margin-right: 0.4em; +} +#pagehistory span.minor { font-weight: bold; } +#pagehistory li { border: 1px solid White; } +#pagehistory li.selected { + background-color:#f9f9f9; + border:1px dashed #aaaaaa; +} + +img { border: none; } + +#toc, +.toc { + border: 1px solid #bba; + background-color: #f7f8ff; + padding: 5px; + font-size: 95%; + text-align: center; +} +#toc h2, +.toc h2 { + display: inline; + border: none; + padding: 0; + font-size: 100%; + font-weight: bold; +} +#toc ul, +.toc ul { + list-style-type: none; + list-style-image: none; + margin-left: 0; + padding-left: 0; + text-align: left; +} +#toc ul ul, +.toc ul ul { + margin: 0 0 0 2em; +} +#toc .toctoggle, +.toc .toctoggle { + font-size: 94%; +} + + +.error { + color: red; + font-size: larger; +} + +/* preference page with js-genrated toc */ +#preftoc { + float: left; + margin: 1em 1em 1em 1em; + width: 13em; +} +#preftoc li { border: 1px solid White; } +#preftoc li.selected { + background-color:#f9f9f9; + border:1px dashed #aaaaaa; +} +#preftoc a, +#preftoc a:active { + display: block; + color: #005189; +} +#prefcontrol { + clear: left; + float: left; + margin-top: 1em; +} +div.prefsectiontip { + font-size: 94%; + margin-top: 0.4em; + color: #666; +} +fieldset.prefsection { margin-top: 1em } +fieldset.operaprefsection { margin-left: 15em } + +/* emulate center */ +.center { + width: 100%; + text-align: center; +} +*.center * { + margin-left: auto; + margin-right: auto; +} +/* small for tables and similar */ +.small, .small * { font-size: 94%; } +table.small { font-size: 100% } + +div.townBox { + position:relative; + float:right; + background:White; + margin-left:1em; + border: 1px solid gray; + padding:0.3em; + width: 200px; + overflow: hidden; + clear: right; +} +div.townBox dl { + padding: 0; + margin: 0 0 0.3em 0; + font-size: 96%; +} +div.townBox dl dt { + background: none; + margin: 0.4em 0 0 0; +} +div.townBox dl dd { + margin: 0.1em 0 0 1.1em; + background-color: #f3f3f3; +} +/* use this instead of #toc for page content */ +.toccolours { + border:1px solid #aaaaaa; + background-color:#f9f9f9; + padding:5px; + font-size: 95%; +} +#siteNotice { + border:1px solid #aaaaaa; + padding-left: 0.5em; + padding-right: 0.5em; +} +.redirectText { + font-size:150%; + margin:5px; +} +.searchmatch { + color: red; + font-weight: bold; +} +.sharedUploadNotice { + font-style: italic; +} +span.unpatrolled { + font-weight:bold; + color:red; +} + +span.updatedmarker { + color:black; + background-color:#00FF00; +} + +table.gallery { + border: 1px solid #cccccc; + margin: 2px; + padding: 2px; + background-color:#ffffff; +} + +table.gallery tr { + vertical-align:top; +} + +table.gallery td { + vertical-align:top; + background-color:#f9f9f9; + border: solid 2px white; +} + +div.gallerybox { + margin: 2px; + width: 150px; +} + +div.gallerybox div.thumb { + text-align: center; + border: 1px solid #cccccc; + margin: 2px; +} + +div.gallerytext { + overflow: hidden; + font-size: 94%; + padding: 2px 4px; +} + +span.comment { + font-style: italic; +} + +span.changedby { + font-size: 95%; +} + +.previewnote { + text-align: center; + color: #cc0000; +} +.editExternally { + border-style:solid; + border-width:1px; + border-color:gray; + background: #ffffff; + padding:3px; + margin-top:0.5em; + float:left; + font-size:small; + text-align:center; +} +.editExternallyHelp { + font-style:italic; + color:gray; +} + +li span.deleted { + text-decoration: line-through; + color: #888; + font-style: italic; +} + +/* Classes for EXIF data display */ +table.mw_metadata { + margin-left: 0.5em; +} + +table.mw_metadata caption { font-weight: bold; } +table.mw_metadata th { font-weight: normal; } +table.mw_metadata td { padding: 0.1em; } + +table.mw_metadata { + border: none; + border-collapse: collapse; +} +table.mw_metadata td, table.mw_metadata th { + border: 1px solid #aaaaaa; + padding-left: 4px; + padding-right: 4px; +} +table.mw_metadata th { + background-color: #f9f9f9; +} +table.mw_metadata td { + background-color: #fcfcfc; +} +table.mw_metadata td.spacer { + background: inherit; + border-top: none; + border-bottom: none; +} +table.collapsed tr.collapsable { + display: none; +} + +.visualClear { + clear: both; +} + +#mw_trackbacks { + border: solid 1px #bbbbff; + background-color: #eeeeff; + padding: 0.2em; +} + +/* Allmessages table */ + +#allmessagestable th { + background-color: #b2b2ff; +} + +#allmessagestable tr.orig { + background-color: #ffe2e2; +} + +#allmessagestable tr.new { + background-color: #e2ffe2; +} + +#allmessagestable tr.def { + background-color: #f0f0ff; +} + +#jump-to-nav { + display: none; +} + +/* Keep this temporarily so that cached pages will display right */ +table.gallery td.galleryheader { + text-align: center; + font-weight: bold; +} +table.gallery caption { + font-weight: bold; +} + +div.multipageimagenavbox { + border: solid 1px silver; + padding: 4px; + margin: 1em; + -moz-border-radius: 6px; + background: #f0f0f0; +} + +div.multipageimagenavbox div.thumb { + border: none; + margin-left: 2em; + margin-right: 2em; +} + +div.multipageimagenavbox hr { + margin: 6px; +} + +table.multipageimage td { + text-align: center; +} + +/* + Table pager (e.g. Special:Imagelist) + - remove underlines from the navigation link + - collapse borders + - set the borders to outsets (similar to Special:Allmessages) + - remove line wrapping for all td and th, set background color + - restore line wrapping for the last two table cells (description and size) +*/ +.TablePager_nav a { text-decoration: none; } +.TablePager { border-collapse: collapse; } +.TablePager, .TablePager td, .TablePager th { + border: 0.15em solid #777777; + padding: 0 0.15em 0 0.15em; +} +.TablePager th { background-color: #eeeeff } +.TablePager td { background-color: #ffffff } +.TablePager tr:hover td { background-color: #eeeeff } + +.imagelist td, .imagelist th { white-space: nowrap } +.imagelist .TablePager_col_links { background-color: #eeeeff } +.imagelist .TablePager_col_img_description { white-space: normal } +.imagelist th.TablePager_sort { background-color: #ccccff } + +.templatesUsed { margin-top: 1em; } + +/* Convenience links on Special:Ipblocklist */ +p.mw-ipb-conveniencelinks { + font-size: 90%; + float: right; +} + +/* Recreating-deleted-page warning and log entries */ +div#mw-recreate-deleted-warn ul li { + font-size: 95%; +} + + +.MediaTransformError { + border: thin solid #777; + background-color: #ccc; + padding: 0.1em; +} +.MediaTransformError td { + text-align: center; + vertical-align: middle; + font-size: 90%; +} diff --git a/skins/common/protect.js b/skins/common/protect.js index d8d1aa1c..b3eec3bd 100644 --- a/skins/common/protect.js +++ b/skins/common/protect.js @@ -1,89 +1,94 @@ -function protectInitialize(tableId, labelText) { - if (document.createTextNode) { - var box = document.getElementById(tableId); - if (!box) - return false; - - var tbody = box.getElementsByTagName('tbody')[0]; - var row = document.createElement('tr'); - tbody.appendChild(row); - - row.appendChild(document.createElement('td')); - var col2 = document.createElement('td'); - row.appendChild(col2); - - var check = document.createElement('input'); - check.id = "mwProtectUnchained"; - check.type = "checkbox"; - check.onclick = protectChainUpdate; - col2.appendChild(check); - - var space = document.createTextNode(" "); - col2.appendChild(space); - - var label = document.createElement('label'); - label.setAttribute("for", "mwProtectUnchained"); - label.appendChild(document.createTextNode(labelText)); - col2.appendChild(label); - - if (protectAllMatch()) { - check.checked = false; - protectEnable(false); - } else { - check.checked = true; - protectEnable(true); - } +/** + * Set up the protection chaining interface (i.e. "unlock move permissions" checkbox) + * on the protection form + * + * @param String tableId Identifier of the table containing UI bits + * @param String labelText Text to use for the checkbox label + */ +function protectInitialize( tableId, labelText ) { + if( !( document.createTextNode && document.getElementById && document.getElementsByTagName ) ) + return false; - allowCascade(); - - return true; - } - return false; + var box = document.getElementById( tableId ); + if( !box ) + return false; + + var tbody = box.getElementsByTagName( 'tbody' )[0]; + var row = document.createElement( 'tr' ); + tbody.appendChild( row ); + + row.appendChild( document.createElement( 'td' ) ); + var col = document.createElement( 'td' ); + row.appendChild( col ); + + var check = document.createElement( 'input' ); + check.id = 'mwProtectUnchained'; + check.type = 'checkbox'; + col.appendChild( check ); + addClickHandler( check, protectChainUpdate ); + + col.appendChild( document.createTextNode( ' ' ) ); + var label = document.createElement( 'label' ); + label.setAttribute( 'for', 'mwProtectUnchained' ); + label.appendChild( document.createTextNode( labelText ) ); + col.appendChild( label ); + + check.checked = !protectAllMatch(); + protectEnable( check.checked ); + + allowCascade(); + + return true; } function allowCascade() { - var pr_types = document.getElementsByTagName("select"); - for (var i = 0; i < pr_types.length; i++) { - if (pr_types[i].id.match(/^mwProtect-level-/)) { - var selected_level = pr_types[i].getElementsByTagName("option")[pr_types[i].selectedIndex].value; - if ( !isCascadeableLevel(selected_level) ) { - document.getElementById('mwProtect-cascade').checked=false; - document.getElementById('mwProtect-cascade').disabled=true; + var lists = protectSelectors(); + for( var i = 0; i < lists.length; i++ ) { + if( lists[i].selectedIndex > -1 ) { + var items = lists[i].getElementsByTagName( 'option' ); + var selected = items[ lists[i].selectedIndex ].value; + if( wgCascadeableLevels.indexOf( selected ) == -1 ) { + document.getElementById( 'mwProtect-cascade' ).checked = false; + document.getElementById( 'mwProtect-cascade' ).disabled = true; return false; } } } - document.getElementById('mwProtect-cascade').disabled=false; + document.getElementById( 'mwProtect-cascade' ).disabled = false; return true; } -function isCascadeableLevel( level ) { - for (var k = 0; k < wgCascadeableLevels.length; k++) { - if ( wgCascadeableLevels[k] == level ) { - return true; - } - } - return false; -} - +/** + * When protection levels are locked together, update the rest + * when one action's level changes + * + * @param Element source Level selector that changed + */ function protectLevelsUpdate(source) { - if (!protectUnchained()) { - protectUpdateAll(source.selectedIndex); - } + if( !protectUnchained() ) + protectUpdateAll( source.selectedIndex ); allowCascade(); } +/** + * Update chain status and enable/disable various bits of the UI + * when the user changes the "unlock move permissions" checkbox + */ function protectChainUpdate() { - if (protectUnchained()) { - protectEnable(true); + if( protectUnchained() ) { + protectEnable( true ); } else { protectChain(); - protectEnable(false); + protectEnable( false ); } allowCascade(); } - +/** + * Are all actions protected at the same level? + * + * @return boolean + */ function protectAllMatch() { var values = new Array(); protectForSelectors(function(set) { @@ -97,17 +102,22 @@ function protectAllMatch() { return true; } +/** + * Is protection chaining on or off? + * + * @return bool + */ function protectUnchained() { - var unchain = document.getElementById("mwProtectUnchained"); - if (!unchain) { - alert("This shouldn't happen"); - return false; - } - return unchain.checked; + var unchain = document.getElementById( 'mwProtectUnchained' ); + return unchain + ? unchain.checked + : true; // No control, so we need to let the user set both levels } +/** + * Find the highest-protected action and set all others to that level + */ function protectChain() { - // Find the highest-protected action and bump them all to this level var maxIndex = -1; protectForSelectors(function(set) { if (set.selectedIndex > maxIndex) { @@ -117,6 +127,11 @@ function protectChain() { protectUpdateAll(maxIndex); } +/** + * Protect all actions at the specified level + * + * @param int index Protection level + */ function protectUpdateAll(index) { protectForSelectors(function(set) { if (set.selectedIndex != index) { @@ -125,6 +140,11 @@ function protectUpdateAll(index) { }); } +/** + * Apply a callback to each protection selector + * + * @param callable func Callback function + */ function protectForSelectors(func) { var selectors = protectSelectors(); for (var i = 0; i < selectors.length; i++) { @@ -132,6 +152,11 @@ function protectForSelectors(func) { } } +/** + * Get a list of all protection selectors on the page + * + * @return Array + */ function protectSelectors() { var all = document.getElementsByTagName("select"); var ours = new Array(); @@ -144,6 +169,11 @@ function protectSelectors() { return ours; } +/** + * Enable/disable protection selectors + * + * @param boolean val Enable? + */ function protectEnable(val) { // fixme var first = true; diff --git a/skins/common/shared.css b/skins/common/shared.css new file mode 100644 index 00000000..f6d63ab8 --- /dev/null +++ b/skins/common/shared.css @@ -0,0 +1,48 @@ +/** + * CSS in this file is used by *all* skins (that have any CSS at all). Be + * careful what you put in here, since what looks good in one skin may not in + * another, but don't ignore the poor non-Monobook users either. + */ +.mw-plusminus-null { color: #aaa; } + +.texvc { direction: ltr; unicode-bidi: embed; } +img.tex { vertical-align: middle; } +span.texhtml { font-family: serif; } + +/* Stop floats from intruding into edit area in previews */ +#toolbar, #wpTextbox1 { clear: both; } + +div#mw-js-message { + margin: 1em 5%; + padding: 0.5em 2.5%; + border: solid 1px #ddd; + background-color: #fcfcfc; +} + +/* Edit section links */ +.editsection { + float: right; + margin-left: 5px; +} + +/** + * File histories + */ +table.filehistory { + border:1px solid #ccc; + border-collapse:collapse; +} + +table.filehistory th, +table.filehistory td { + padding: 0 0.2em 0 0.2em; + vertical-align:top; + border:1px solid #ccc; +} +table.filehistory th { + text-align: left; +} +table.filehistory td.mw-imagepage-filesize, +table.filehistory th.mw-imagepage-filesize { + white-space:nowrap; +} diff --git a/skins/common/upload.js b/skins/common/upload.js index 160fbf27..7cbfc9aa 100644 --- a/skins/common/upload.js +++ b/skins/common/upload.js @@ -1,23 +1,176 @@ function licenseSelectorCheck() { - var selector = document.getElementById("wpLicense"); - if (selector.selectedIndex > 0 && - selector.options[selector.selectedIndex].value == "" ) { - // Browser is broken, doesn't respect disabled attribute on <option> - selector.selectedIndex = 0; + var selector = document.getElementById( "wpLicense" ); + var selection = selector.options[selector.selectedIndex].value; + if( selector.selectedIndex > 0 ) { + if( selection == "" ) { + // Option disabled, but browser is broken and doesn't respect this + selector.selectedIndex = 0; + } } + // We might show a preview + wgUploadLicenseObj.fetchPreview( selection ); } function licenseSelectorFixup() { // for MSIE/Mac; non-breaking spaces cause the <option> not to render // but, for some reason, setting the text to itself works var selector = document.getElementById("wpLicense"); - var ua = navigator.userAgent; - var isMacIe = (ua.indexOf("MSIE") != -1) && (ua.indexOf("Mac") != -1); - if (isMacIe) { - for (var i = 0; i < selector.options.length; i++) { - selector.options[i].text = selector.options[i].text; + if (selector) { + var ua = navigator.userAgent; + var isMacIe = (ua.indexOf("MSIE") != -1) && (ua.indexOf("Mac") != -1); + if (isMacIe) { + for (var i = 0; i < selector.options.length; i++) { + selector.options[i].text = selector.options[i].text; + } + } + } +} + +var wgUploadWarningObj = { + 'responseCache' : { '' : ' ' }, + 'nameToCheck' : '', + 'typing': false, + 'delay': 500, // ms + 'timeoutID': false, + + 'keypress': function () { + if ( !wgAjaxUploadDestCheck || !sajax_init_object() ) return; + + // Find file to upload + var destFile = document.getElementById('wpDestFile'); + var warningElt = document.getElementById( 'wpDestFile-warning' ); + if ( !destFile || !warningElt ) return ; + + this.nameToCheck = destFile.value ; + + // Clear timer + if ( this.timeoutID ) { + window.clearTimeout( this.timeoutID ); + } + // Check response cache + for (cached in this.responseCache) { + if (this.nameToCheck == cached) { + this.setWarning(this.responseCache[this.nameToCheck]); + return; + } + } + + this.timeoutID = window.setTimeout( 'wgUploadWarningObj.timeout()', this.delay ); + }, + + 'checkNow': function (fname) { + if ( !wgAjaxUploadDestCheck || !sajax_init_object() ) return; + if ( this.timeoutID ) { + window.clearTimeout( this.timeoutID ); } + this.nameToCheck = fname; + this.timeout(); + }, + + 'timeout' : function() { + if ( !wgAjaxUploadDestCheck || !sajax_init_object() ) return; + injectSpinner( document.getElementById( 'wpDestFile' ), 'destcheck' ); + + // Get variables into local scope so that they will be preserved for the + // anonymous callback. fileName is copied so that multiple overlapping + // ajax requests can be supported. + var obj = this; + var fileName = this.nameToCheck; + sajax_do_call( 'UploadForm::ajaxGetExistsWarning', [this.nameToCheck], + function (result) { + obj.processResult(result, fileName) + } + ); + }, + + 'processResult' : function (result, fileName) { + removeSpinner( 'destcheck' ); + this.setWarning(result.responseText); + this.responseCache[fileName] = result.responseText; + }, + + 'setWarning' : function (warning) { + var warningElt = document.getElementById( 'wpDestFile-warning' ); + var ackElt = document.getElementById( 'wpDestFileWarningAck' ); + this.setInnerHTML(warningElt, warning); + + // Set a value in the form indicating that the warning is acknowledged and + // doesn't need to be redisplayed post-upload + if ( warning == '' || warning == ' ' ) { + ackElt.value = ''; + } else { + ackElt.value = '1'; + } + }, + + 'setInnerHTML' : function (element, text) { + // Check for no change to avoid flicker in IE 7 + if (element.innerHTML != text) { + element.innerHTML = text; + } + } +} + +function fillDestFilename(id) { + if (!document.getElementById) { + return; + } + var path = document.getElementById(id).value; + // Find trailing part + var slash = path.lastIndexOf('/'); + var backslash = path.lastIndexOf('\\'); + var fname; + if (slash == -1 && backslash == -1) { + fname = path; + } else if (slash > backslash) { + fname = path.substring(slash+1, 10000); + } else { + fname = path.substring(backslash+1, 10000); + } + + // Capitalise first letter and replace spaces by underscores + fname = fname.charAt(0).toUpperCase().concat(fname.substring(1,10000)).replace(/ /g, '_'); + + // Output result + var destFile = document.getElementById('wpDestFile'); + if (destFile) { + destFile.value = fname; + wgUploadWarningObj.checkNow(fname) ; + } +} + +var wgUploadLicenseObj = { + + 'responseCache' : { '' : '' }, + + 'fetchPreview': function( license ) { + if( !wgAjaxLicensePreview || !sajax_init_object() ) return; + for (cached in this.responseCache) { + if (cached == license) { + this.showPreview( this.responseCache[license] ); + return; + } + } + injectSpinner( document.getElementById( 'wpLicense' ), 'license' ); + sajax_do_call( 'UploadForm::ajaxGetLicensePreview', [license], + function( result ) { + wgUploadLicenseObj.processResult( result, license ); + } + ); + }, + + 'processResult' : function( result, license ) { + removeSpinner( 'license' ); + this.showPreview( result.responseText ); + this.responseCache[license] = result.responseText; + }, + + 'showPreview' : function( preview ) { + var previewPanel = document.getElementById( 'mw-license-preview' ); + if( previewPanel.innerHTML != preview ) + previewPanel.innerHTML = preview; } + } -addOnloadHook(licenseSelectorFixup); +addOnloadHook( licenseSelectorFixup );
\ No newline at end of file diff --git a/skins/common/wikibits.js b/skins/common/wikibits.js index 6299e5fa..11ede270 100644 --- a/skins/common/wikibits.js +++ b/skins/common/wikibits.js @@ -12,6 +12,7 @@ if (clientPC.indexOf('opera') != -1) { var is_opera = true; var is_opera_preseven = (window.opera && !document.childNodes); var is_opera_seven = (window.opera && document.childNodes); + var is_opera_95 = (clientPC.search(/opera\/(9.[5-9]|[1-9][0-9])/)!=-1); } // Global external objects used by this script. @@ -41,8 +42,10 @@ function hookEvent(hookName, hookFunct) { if (typeof stylepath != 'undefined' && typeof skin != 'undefined') { if (is_opera_preseven) { document.write('<link rel="stylesheet" type="text/css" href="'+stylepath+'/'+skin+'/Opera6Fixes.css">'); - } else if (is_opera_seven) { + } else if (is_opera_seven && !is_opera_95) { document.write('<link rel="stylesheet" type="text/css" href="'+stylepath+'/'+skin+'/Opera7Fixes.css">'); + } else if (is_opera_95) { + document.write('<link rel="stylesheet" type="text/css" href="'+stylepath+'/'+skin+'/Opera95Fixes.css">'); } else if (is_khtml) { document.write('<link rel="stylesheet" type="text/css" href="'+stylepath+'/'+skin+'/KHTMLFixes.css">'); } @@ -373,7 +376,8 @@ function mwSetupToolbar() { // Don't generate buttons for browsers which don't fully // support it. - if (!document.selection && textbox.selectionStart === null) { + if (!(document.selection && document.selection.createRange) + && textbox.selectionStart === null) { return false; } @@ -408,7 +412,6 @@ function escapeQuotesHTML(text) { // apply tagOpen/tagClose to selection in textarea, // use sampleText instead of selection if there is none -// copied and adapted from phpBB function insertTags(tagOpen, tagClose, sampleText) { var txtarea; if (document.editform) { @@ -418,62 +421,72 @@ function insertTags(tagOpen, tagClose, sampleText) { var areas = document.getElementsByTagName('textarea'); txtarea = areas[0]; } + var selText, isSample = false; - // IE - if (document.selection && !is_gecko) { - var theSelection = document.selection.createRange().text; - if (!theSelection) { - theSelection=sampleText; - } + if (document.selection && document.selection.createRange) { // IE/Opera + + //save window scroll position + if (document.documentElement && document.documentElement.scrollTop) + var winScroll = document.documentElement.scrollTop + else if (document.body) + var winScroll = document.body.scrollTop; + //get current selection txtarea.focus(); - if (theSelection.charAt(theSelection.length - 1) == " ") { // exclude ending space char, if any - theSelection = theSelection.substring(0, theSelection.length - 1); - document.selection.createRange().text = tagOpen + theSelection + tagClose + " "; - } else { - document.selection.createRange().text = tagOpen + theSelection + tagClose; + var range = document.selection.createRange(); + selText = range.text; + //insert tags + checkSelectedText(); + range.text = tagOpen + selText + tagClose; + //mark sample text as selected + if (isSample && range.moveStart) { + if (window.opera) + tagClose = tagClose.replace(/\n/g,''); + range.moveStart('character', - tagClose.length - selText.length); + range.moveEnd('character', - tagClose.length); } - - // Mozilla - } else if(txtarea.selectionStart || txtarea.selectionStart == '0') { - var replaced = false; + range.select(); + //restore window scroll position + if (document.documentElement && document.documentElement.scrollTop) + document.documentElement.scrollTop = winScroll + else if (document.body) + document.body.scrollTop = winScroll; + + } else if (txtarea.selectionStart || txtarea.selectionStart == '0') { // Mozilla + + //save textarea scroll position + var textScroll = txtarea.scrollTop; + //get current selection + txtarea.focus(); var startPos = txtarea.selectionStart; var endPos = txtarea.selectionEnd; - if (endPos-startPos) { - replaced = true; - } - var scrollTop = txtarea.scrollTop; - var myText = (txtarea.value).substring(startPos, endPos); - if (!myText) { - myText=sampleText; - } - var subst; - if (myText.charAt(myText.length - 1) == " ") { // exclude ending space char, if any - subst = tagOpen + myText.substring(0, (myText.length - 1)) + tagClose + " "; - } else { - subst = tagOpen + myText + tagClose; - } - txtarea.value = txtarea.value.substring(0, startPos) + subst + - txtarea.value.substring(endPos, txtarea.value.length); - txtarea.focus(); + selText = txtarea.value.substring(startPos, endPos); + //insert tags + checkSelectedText(); + txtarea.value = txtarea.value.substring(0, startPos) + + tagOpen + selText + tagClose + + txtarea.value.substring(endPos, txtarea.value.length); //set new selection - if (replaced) { - var cPos = startPos+(tagOpen.length+myText.length+tagClose.length); - txtarea.selectionStart = cPos; - txtarea.selectionEnd = cPos; + if (isSample) { + txtarea.selectionStart = startPos + tagOpen.length; + txtarea.selectionEnd = startPos + tagOpen.length + selText.length; } else { - txtarea.selectionStart = startPos+tagOpen.length; - txtarea.selectionEnd = startPos+tagOpen.length+myText.length; + txtarea.selectionStart = startPos + tagOpen.length + selText.length + tagClose.length; + txtarea.selectionEnd = txtarea.selectionStart; } - txtarea.scrollTop = scrollTop; + //restore textarea scroll position + txtarea.scrollTop = textScroll; + } - // All other browsers get no toolbar. - // There was previously support for a crippled "help" - // bar, but that caused more problems than it solved. - } - // reposition cursor if possible - if (txtarea.createTextRange) { - txtarea.caretPos = document.selection.createRange().duplicate(); + function checkSelectedText(){ + if (!selText) { + selText = sampleText; + isSample = true; + } else if (selText.charAt(selText.length - 1) == ' ') { //exclude ending space char + selText = selText.substring(0, selText.length - 1); + tagClose += ' ' + } } + } @@ -604,8 +617,7 @@ function akeytt( doId ) { // the original. var ta; if ( doId ) { - ta = new Array; - ta[doId] = window.ta[doId]; + ta = [doId]; } else { ta = window.ta; } @@ -713,8 +725,10 @@ function addCheckboxClickHandlers(inputs, start) { var cb = inputs[i]; if ( !cb.type || cb.type.toLowerCase() != 'checkbox' ) continue; - cb.index = checkboxes.push(cb) - 1; - cb.onmouseup = checkboxMouseupHandler; + var end = checkboxes.length; + checkboxes[end] = cb; + cb.index = end; + cb.onclick = checkboxClickHandler; } if ( finish < inputs.length ) { @@ -724,7 +738,7 @@ function addCheckboxClickHandlers(inputs, start) { } } -function checkboxMouseupHandler(e) { +function checkboxClickHandler(e) { if (typeof e == 'undefined') { e = window.event; } @@ -732,10 +746,7 @@ function checkboxMouseupHandler(e) { lastCheckbox = this.index; return true; } - var endState = !this.checked; - if ( is_opera ) { // opera has already toggled the checkbox by this point - endState = !endState; - } + var endState = this.checked; var start, finish; if ( this.index < lastCheckbox ) { start = this.index + 1; @@ -767,47 +778,23 @@ function toggle_element_check(ida,idb) { document.getElementById(idb).checked=false; } -function fillDestFilename(id) { - if (!document.getElementById) { - return; - } - var path = document.getElementById(id).value; - // Find trailing part - var slash = path.lastIndexOf('/'); - var backslash = path.lastIndexOf('\\'); - var fname; - if (slash == -1 && backslash == -1) { - fname = path; - } else if (slash > backslash) { - fname = path.substring(slash+1, 10000); - } else { - fname = path.substring(backslash+1, 10000); - } - - // Capitalise first letter and replace spaces by underscores - fname = fname.charAt(0).toUpperCase().concat(fname.substring(1,10000)).replace(/ /g, '_'); - - // Output result - var destFile = document.getElementById('wpDestFile'); - if (destFile) { - destFile.value = fname; - } -} - +/** + * Restore the edit box scroll state following a preview operation, + * and set up a form submission handler to remember this state + */ function scrollEditBox() { - var editBoxEl = document.getElementById("wpTextbox1"); - var scrollTopEl = document.getElementById("wpScrolltop"); - var editFormEl = document.getElementById("editform"); - - if (editBoxEl && scrollTopEl) { - if (scrollTopEl.value) { editBoxEl.scrollTop = scrollTopEl.value; } - editFormEl.onsubmit = function() { - document.getElementById("wpScrolltop").value = document.getElementById("wpTextbox1").scrollTop; - }; + var editBox = document.getElementById( 'wpTextbox1' ); + var scrollTop = document.getElementById( 'wpScrolltop' ); + var editForm = document.getElementById( 'editform' ); + if( editBox && scrollTop ) { + if( scrollTop.value ) + editBox.scrollTop = scrollTop.value; + addHandler( editForm, 'submit', function() { + document.getElementById( 'wpScrolltop' ).value = document.getElementById( 'wpTextbox1' ).scrollTop; + } ); } } - -hookEvent("load", scrollEditBox); +hookEvent( 'load', scrollEditBox ); var allmessages_nodelist = false; var allmessages_modified = false; @@ -905,11 +892,13 @@ function getElementsByClassName(oElm, strTagName, oClassNames){ var arrRegExpClassNames = new Array(); if(typeof oClassNames == "object"){ for(var i=0; i<oClassNames.length; i++){ - arrRegExpClassNames.push(new RegExp("(^|\\s)" + oClassNames[i].replace(/\-/g, "\\-") + "(\\s|$)")); + arrRegExpClassNames[arrRegExpClassNames.length] = + new RegExp("(^|\\s)" + oClassNames[i].replace(/\-/g, "\\-") + "(\\s|$)"); } } else{ - arrRegExpClassNames.push(new RegExp("(^|\\s)" + oClassNames.replace(/\-/g, "\\-") + "(\\s|$)")); + arrRegExpClassNames[arrRegExpClassNames.length] = + new RegExp("(^|\\s)" + oClassNames.replace(/\-/g, "\\-") + "(\\s|$)"); } var oElement; var bMatchesAll; @@ -923,7 +912,7 @@ function getElementsByClassName(oElm, strTagName, oClassNames){ } } if(bMatchesAll){ - arrReturnElements.push(oElement); + arrReturnElements[arrReturnElements.length] = oElement; } } return (arrReturnElements) @@ -1010,7 +999,8 @@ function ts_makeSortable(table) { function ts_getInnerText(el) { if (typeof el == "string") return el; if (typeof el == "undefined") { return el }; - if (el.innerText) return el.innerText; // Not needed but it is faster + if (el.textContent) return el.textContent; // not needed but it is faster + if (el.innerText) return el.innerText; // IE doesn't have textContent var str = ""; var cs = el.childNodes; @@ -1213,6 +1203,83 @@ function ts_alternate(table) { /* * End of table sorting code */ + + +/** + * Add a cute little box at the top of the screen to inform the user of + * something, replacing any preexisting message. + * + * @param String message HTML to be put inside the right div + * @param String className Used in adding a class; should be different for each + * call to allow CSS/JS to hide different boxes. null = no class used. + * @return Boolean True on success, false on failure + */ +function jsMsg( message, className ) { + if ( !document.getElementById ) { + return false; + } + // We special-case skin structures provided by the software. Skins that + // choose to abandon or significantly modify our formatting can just define + // an mw-js-message div to start with. + var messageDiv = document.getElementById( 'mw-js-message' ); + if ( !messageDiv ) { + messageDiv = document.createElement( 'div' ); + if ( document.getElementById( 'column-content' ) + && document.getElementById( 'content' ) ) { + // MonoBook, presumably + document.getElementById( 'content' ).insertBefore( + messageDiv, + document.getElementById( 'content' ).firstChild + ); + } else if ( document.getElementById('content') + && document.getElementById( 'article' ) ) { + // Non-Monobook but still recognizable (old-style) + document.getElementById( 'article').insertBefore( + messageDiv, + document.getElementById( 'article' ).firstChild + ); + } else { + return false; + } + } + + messageDiv.setAttribute( 'id', 'mw-js-message' ); + if( className ) { + messageDiv.setAttribute( 'class', 'mw-js-message-'+className ); + } + messageDiv.innerHTML = message; + return true; +} + +/** + * Inject a cute little progress spinner after the specified element + * + * @param element Element to inject after + * @param id Identifier string (for use with removeSpinner(), below) + */ +function injectSpinner( element, id ) { + var spinner = document.createElement( "img" ); + spinner.id = "mw-spinner-" + id; + spinner.src = stylepath + "/common/images/spinner.gif"; + spinner.alt = spinner.title = "..."; + if( element.nextSibling ) { + element.parentNode.insertBefore( spinner, element.nextSibling ); + } else { + element.parentNode.appendChild( spinner ); + } +} + +/** + * Remove a progress spinner added with injectSpinner() + * + * @param id Identifier string + */ +function removeSpinner( id ) { + var spinner = document.getElementById( "mw-spinner-" + id ); + if( spinner ) { + spinner.parentNode.removeChild( spinner ); + } +} function runOnloadHook() { // don't run anything below this for non-dom browsers @@ -1239,8 +1306,31 @@ function runOnloadHook() { } } +/** + * Add an event handler to an element + * + * @param Element element Element to add handler to + * @param String attach Event to attach to + * @param callable handler Event handler callback + */ +function addHandler( element, attach, handler ) { + if( window.addEventListener ) { + element.addEventListener( attach, handler, false ); + } else if( window.attachEvent ) { + element.attachEvent( 'on' + attach, handler ); + } +} + +/** + * Add a click event handler to an element + * + * @param Element element Element to add handler to + * @param callable handler Event handler callback + */ +function addClickHandler( element, handler ) { + addHandler( element, 'click', handler ); +} //note: all skins should call runOnloadHook() at the end of html output, // so the below should be redundant. It's there just in case. hookEvent("load", runOnloadHook); - hookEvent("load", mwSetupToolbar); |