User:Alex Smotrov/Draft
From Wikipedia, the free encyclopedia
Small guide on writing user scripts for Wikimedia sites. Of course, some basic Javascript knowledge is required.
[edit] Scripts
The following script files are executed for every Wikipedia visitor:
- some (wg) variables in the beginning of the page
- wikibits.js — shared by all Wikimedia projects
- generated — code from MediaWiki:Common.js, supported by local Administrators
- monobook.js — your own script file, if you created one
- ajax.js — shared by all Wikimedia projects
It's recommended that you save the «system» script files locally and view them with text editor (with syntax highlighting). There are some useful functions there that you can use in your scripts, some of them are mentioned below.
[edit] Structure
When your monobook.js is executed most HTML page elements do not exist yet. So most user scripts look like this:
//part 1 addOnloadHook(func_start); //means «execute func_start later»
//part 2 — executed when the page is loaded function func_start (){ //quite often it simply adds a javascript link <a onclick="func_action()" href="#"> } //and then there is …
//part 3 — executed when user clicks on this link
function func_action (){
}
[edit] Basic methods
[edit] Finding elements
Every HTML element is a node of DOM model which allows scripts to access the element. For example on this page
<form name="frmname" id="frmid"> <textarea name="txtname" id="txtid"> <input id="neighbor">
we can «find» element textarea:
- using it's id: document.getElementById('txtid')
- in the array of all elements with the same tag: document.getElementsByTagName('textarea')[0]
- using element next to it: document.getElementById('neighbor').previousSibling
- as a child of its parent: document.getElementById('frmid').childNodes[0]
- as a form element, using name: document.frmname.txtname
For more info about DOM nodes attributes and methods see w3schools or mozilla.org. To see all the elements on the page and their relations simply look at the page source code.
[edit] Checking the page
Many scripts are supposed to work only on some pages. You can check:
- page address
if (document.URL.indexOf('&action=history') != -1) {
//continue only on history pages
- wg variables; many of them have the same meaning as Magic words
if (wgCanonicalNamespace == 'User_talk') {
//continue only on User_talk pages
- presense of elements (only in 2nd and 3rd parts of the script)
function func_start () {
if (!document.editform) return; //no edit form → exit
… …
[edit] portlets
Usual places to add your own links — portlet blocks with these id's:
p-logo | p-personal name my talk my preferences … |
p-cactions article discussion edit this page … | |
p-navigation p-search p-tb p-lang |
Portlet structure: <div id='…' class=portlet> <h5>Header</h5> <div class=pBody> <ul> <li id='…'> <a …> //links <li id='…'> <a …> … … |
There is a special function in wikibits.js that simplifies the process of adding your own links into portlets:
addPortletLink (portlet, href, text, id, tooltip, accesskey, nextnode)
//Example: add the link into «toolbox» portlet
addPortletLink ('p-tb', '/wiki/Special:MyPage/monobook.js', 'My monobook.js');
Last 4 arguments are optional; all arguments are explained in the code.
[edit] Adding elements
In all other cases there are two ways to insert new elements:
1) adding them to innerHTML of the parent element
//Example: using innerHTML to create a new portlet
document.getElementById('p-participation').innerHTML +=
'</div>'+
'<div id=my class=portlet>'+
'<h5>mine</h5>'+
'<div class=pBody><ul>'+
'<li><a href=\"/wiki/Special:MyPage/monobook.js\">My monobook.js</a>'+
'</ul></div></div>';
2) using DOM methods: CreateElement, then atach as child using AppendChild or InsertBefore. For examples of usage see the code of addPortletLink()
[edit] Removing elements
To move an element simply attach it in another place with AppendChild or InsertBefore.
To hide an element you can set its style.display
to none
:
//Example: remove copyright warning from edit page
var el = document.getElementById('editpage-copywarn');
if (el) el.style.display = 'none';
This is easier with your monobook.css though: #editpage-copywarn {display:none}
[edit] Edit page
[edit] Text manipulation
The most important element on the edit page is a <textarea> with the article text inside. You can reference it with
var txt = document.editform.wpTextbox1
// or
var txt = document.getElementById('wpTextbox1')
You can add new text to the beginning: txt += "new phrase"
or to the end: txt = "new phrase" + txt
For adding new text to the cursor position there is a special function in wikibits.js:
insertTags (tagOpen, tagClose, sampleText)
[edit] Toolbar
Buttons above textarea are located inside <div id='toolbar'>
.
Standart buttons call insertTags() when clicked. They are defined in the mwEditButtons[] and mwCustomEditButtons[] arrays. Then the buttons are created by mwSetupToolbar() in wikibits.js, but it happens after the 2nd part of your script is called by addOnloadHook.
So if you want to modify some buttons, the easiest way is to simply modify those arrays.
//Example: modify signature button.
if (mwEditButtons.length >= 10 && mwEditButtons[9].tagOpen == '--~~~~')
mwEditButtons[9].tagOpen = ' — ~~~~';
Also see en:User:MarkS/Extra_edit_buttons.
[edit] Edittools
There is another edit panel under textarea. It has a lot of javascript links to the same insertTags(). It's generated from MediaWiki:Edittools by meta:Extension:CharInsert.
//Example: adding your own quick insert to Edittools
var specialchars = document.getElementById ('editpage-specialchars');
specialchars.innerHTML +=
"<a onclick=\"insertTags('<div>','</div>','');return false\"
href='#'><div></a>";
There is no crucial difference between toolbar and edittools, you can insert your own custom links into both.
[edit] Debugging
[edit] Previewing in Monobook.js
You can edit your script directly on your monobook.js page, then press «Show preview» and the new code is executed right away on the preview page.
[edit] Saving in Monobook.js
If required elements are missing on the preview page (for example, your script does something on history pages), you will have to save the script in order to test it.
However it's not convinient and creates unnecessary load on WikiMedia servers.
[edit] Call from Monobook.js
The best and most recommended way is to insert into your monobook.js
document.write('<script type="text/javascript" src="http://localhost/test.js"><\/script>');
Then run any webserver on your computer and create test.js file in the appropriate folder. The code inside this file will be executed as if it was inside monobook.js
You can edit your test.js with any text editor with syntax highlighting and other convinient features, then save the file and simply update any Wikipedia page.
For example you could use TinyWeb which is less 100kbyte on disk and doesn't require installation. Save and unzip tinyweb.zip for example into c:\Program Files\Tinyweb, then create a shortcut to tiny.exe, in shortcut properties add an argument — path to your folder with test.js and any file index.html (required). Start TinyWeb with this shortcut; unload it with Task Manager.
[edit] Other methods
You can also debug your scripts:
- in FireFox with Greasemonkey
- in Opera with User JavaScript
- in Internet Explorer 6 (and maybe in some other browsers) with bookmarklet
javascript: var s = document.createElement('script'); s.src = 'file://C:/myscript.js'; document.getElementsByTagName('head')[0].appendChild(s);void 0
However all these methods execute your user script at slightly different time than monobook.js, so you might have to do some temporary code modifications during debugging.
[edit] Pieces of code
You can run pieces of code on already loaded pages, for example directly in the browser address field: javascript: var s = document.title; alert(s);
Or you can use bookmarklet «JavaScript Shell». It opens new browser window where you can paste or type your code and run it in the context of the current page.
However a full-blown Javascript debugger is much more convinient.
[edit] Software
Any text editor will do. If you plan to use non-ascii characters in string, your text editor should support UTF-8.
Notepad++ is recommended, since it can:
- highlight Javascript code
- quickly insert standart Javascript keywords and methods with Ctrl-Enter
- show the list of all functions and quickly jump to any function
- Code folding
For debugging in Firefox you can use Tools → Javascript Console which shows all Javascript and CSS errors. FireBug is strongly recommended for convenient debugging.
For debugging in IE see IEBlog: Scripting Debugging in Internet Explorer