User:Unready/ui.refresh.js
Appearance
Code that you insert on this page could contain malicious content capable of compromising your account. If you import a script from another page with "importScript", "mw.loader.load", "iusc", or "lusc", take note that this causes you to dynamically load a remote script, which could be changed by others. Editors are responsible for all edits and actions they perform, including by scripts. User scripts are not centrally supported and may malfunction or become inoperable due to software changes. A guide to help you find broken scripts is available. If you are unsure whether code you are adding to this page is safe, you can ask at the appropriate village pump. This code will be executed when previewing this page. |
![]() | Documentation for this user script can be added at User:Unready/ui.refresh. This user script seems to have an accompanying .css page at User:Unready/ui.refresh.css. |
/*
* Description:
* Refresh page content periodically
*
* Version 1.0: 27 April 2015
* Original version for Wikipedia use
* Version 1.1: 28 April 2015
* Use jQuery
* Version 1.2: 29 April 2015
* Dynamically determine selector
* Allow interval configuration
*
* License: CC-BY-SA
* http://creativecommons.org/licenses/by-sa/3.0/
*/
if ( mediaWiki.config.get( 'wgAction' ) !== 'view' )
{
return;
}
(( window.user = window.user || {} ).ui = window.user.ui || {} ).refresh =
( function ( $ )
{
'use strict';
var g_self,
g_selector,
g_jqContent, g_jqInput, g_jqImg,
g_interval = 120, // default refresh interval (seconds)
g_hTimeout = -1; // cannot run = -1; okay to run = 0; running > 0
// get interval (sec) from module properties
// and convert it to msec
function getInterval()
{
if (( typeof g_self.interval === 'number' ) &&
( g_self.interval > 0 ) &&
( g_self.interval < 2592000 )) // 30 days
{
g_interval = g_self.interval;
}
else
{
g_self.interval = g_interval;
}
return g_interval * 1000;
}
// process checkbox events
function onCheck()
{
if ( g_jqInput.prop( 'checked' ))
{
if ( g_hTimeout === 0 )
{ // schedule a tick
g_jqImg.hide(); // in case it was showing after an error
g_hTimeout = window.setTimeout( onTick, getInterval() );
g_self.message = 'OK';
}
}
else
{
if ( g_hTimeout > 0 )
{ // stop the scheduled tick
window.clearTimeout( g_hTimeout );
g_hTimeout = 0;
g_self.message = 'Stopped';
}
}
}
// process Ajax done event
function onDone( htmlString )
{
var jqNewContent,
i;
// strip off body tags
// use search, because match could be too big for replace
i = htmlString.search( /<\s*body[^>]*>/i );
if ( i === -1 )
{
g_self.message = 'onDone :: unable to find html body';
g_jqInput.prop( 'checked', false );
return;
}
htmlString = htmlString.substr( i )
.replace( /^<\s*body[^>]*>\s*/i, '' )
.replace( /\s*<\s*\/html[^>]*>\s*$/i, '' )
.replace( /\s*<\s*\/body[^>]*>\s*$/i, '' );
// force it to parse
jqNewContent = $( htmlString ).find( g_selector );
if ( jqNewContent.length !== 1 )
{
g_self.message = 'onDone :: ' + jqNewContent.length +
' elements found for ( ' + g_selector + ' )';
g_jqInput.prop( 'checked', false );
return;
}
// refresh content
g_jqContent.replaceWith( jqNewContent );
g_jqContent = jqNewContent;
// go back to sleep
g_jqImg.hide();
g_hTimeout = window.setTimeout( onTick, getInterval() );
}
// process Ajax fail event
function onFail( jqDummy, textStatus, errorThrown )
{
g_self.message = 'onFail :: ' + textStatus + ' ' + errorThrown;
g_jqInput.prop( 'checked', false );
}
// handle timer events,
function onTick()
{
g_hTimeout = 0;
g_jqImg.show();
// ajax defaults to window.location.href
$.ajax({ dataType: 'html' })
.done( onDone )
.fail( onFail );
}
// init g_self before document.ready
// in case document.ready executes immediately
g_self =
{
interval : g_interval,
message : 'Initializing',
version : 'Version 1.2.1: 30 April 2015'
};
$( function main()
{
var jqSpan,
i, done,
selectors =
[
'.mw-changeslist', // only on RecentChanges & Watchlist ?
'#mw-content-text' // universally usable ?
],
uriData =
[
'data:image/gif;base64,',
'R0lGODlhKwALAMIAAP///wAAAIKCggAAAP///////////////yH/C05FVFNDQVBF',
'Mi4wAwEAAAAh+QQFCgADACwAAAAAKwALAAADNDiyzPNQtRbhpHfWTCP/mgduYEl+',
'Z8mlGauG1ii+7bzadBejeL64sIfvAtQJR7yioHJsJQAAIfkEBQoAAgAsAAAAAAsA',
'CwAAAw0os8zaMMpJq70YPykSACH5BAUKAAEALAAAAAAbAAsAAAMtGLLM8TCMSalq',
'WERZ+8jY5nVgI45U6URoqmps+71n+8KQPKs1evejC2jzaAUSACH5BAEKAAEALBAA',
'AAAbAAsAAAMtGLLM8TCMSalqWERZ+8jY5nVgI45U6URoqmps+71n+8KQPKs1evej',
'C2jzaAUSADs='
].join( '' ),
htmlString =
[
'<span style="font-size: 40%; margin: 5px; vertical-align: middle;">',
'<label for="ui-refresh-input" title="Enable auto-refresh"',
' style="border-bottom: 1px dotted;">Auto-refresh:</label>',
'<input id="ui-refresh-input" type="checkbox"',
' style="vertical-align: middle;">',
'<img src="' + uriData + '" alt="Refreshing page">',
'</span>'
].join( '' );
// determine the "best" selector
done = false;
for ( i = 0 ; ( i < selectors.length ) && !done ; ++i )
{
g_selector = selectors[i];
g_jqContent = $( g_selector );
done = ( g_jqContent.length === 1 );
}
if ( !done )
{
g_self.message = 'main :: No suitable selector';
return;
}
// span with all the new DOM elements
jqSpan = $( htmlString );
// checkbox checked, with handler
g_jqInput = jqSpan.find( 'input' )
.prop( 'checked', true )
.click( onCheck );
// throbber, initially hidden
g_jqImg = jqSpan.find( 'img' )
.hide();
// add span to h1
if ( $( '#firstHeading:visible' ).append( jqSpan ).length !== 1 )
{
g_self.message = 'main :: Problem with ( #firstHeading:visible )';
g_jqInput.prop( 'checked', false )
.prop( 'disabled', true );
return;
}
// done with DOM
g_hTimeout = window.setTimeout( onTick, getInterval() );
g_self.message = 'OK';
});
return g_self;
}( jQuery ));