Help:Making templates

From YPPedia

Preface

Those who are learning how to design templates from scratch should skip this section.


Templates 101

This article assumes the reader has read (and understood) the Help:Templates page.

Making a template is easy.

  1. Select the name of the template wanted.
  2. Navigate to http://yppedia.puzzlepirates.com/Template:NAME where NAME is the needed template.
  3. Write the template
  4. Press submit

And then the template is ready for using. Of course, writing the template is much more complex than that. Here are some basic template rules:

  1. Template names are case sensitive; Template:Infobox flag may exist, but Template:InFOBox FlAG, or even Template:Infobox Flag doesn't.
  2. Parameters are defined as such: {{{1}}}. This will tell the template that when it is called, to substitute {{{1}}} with whatever comes after 1= in the template.
  3. Numbers do not have to be used, instead a template could be defined using {{{word}}}. Take care though that the user will have to type in |word=something|, instead of just |something| (in the correct place.
  4. Each different parameter must be given a different name. {{{1}}}, {{{2}}}, {{{3}}} are fine for different actions required. {{{1}}}, {{{2}}}, {{{1}}} is sufficient if the third bit needs the same function applied as the first bit, but otherwise will not behave as expected.
  5. It is possible to have multiple names to define a parameter, for example:
    • If {{{first}}} is undefined, use {{{1st}}}
    • If both the above are undefined, use {{{1}}}
    • If all three of the above are undefined, write something blatant to tell the editor that the template is not being used properly.

This requires the use of parameter defaults; see later.

Examples

Nothing special

Template:Nothing special contains the following text:

{{{1}}}<noinclude>[[Category:Help templates]]</noinclude>

(The functional part of this template is in bold. The rest of it is to categorize it in a list of templates used on the help pages, and then to not include such categories on pages which use the template.)

The following table shows what the input and output of certain things are:

Example User input User output
1 {{Nothing special|Hello.}} Hello.
2 {{Nothing special|1=Hello.}} Hello.
3 {{Nothing special|2=Hello.}} {{{1}}}
4 {{Nothing special|Hi!}} Hi!
5 {{Nothing special|This is an equals sign: =}} {{{1}}}
6 {{Nothing special|1=This is an equals sign: =}} This is an equals sign: =
7 {{Nothing special|| <<This is a pipe}} {{{1}}}
8 {{Nothing special|<nowiki>| <<This is a pipe}}</nowiki> | <<This is a pipe

Extra care must be taken when using tables and templates, as they both share a common character of a pipe symbol. In fact, example 7 of the above table resulted in this, and so had to have an output manually typed out. This is because they can easily be confused by the browser (which has no intuition), resulting in extremely strange layouts like this:

Example User input User output
6 {{Nothing special|1=This is an equals sign: =}} This is an equals sign: =
7 {{Nothing special|| <<This is a pipe}} 8 {{Nothing special|<nowiki>| <<This is a pipe}}</nowiki> | <<This is a pipe

Here, the double pipe made the table add an extra column, and has completely booched things for the worst. To the untrained eye, this is a very subtle error, and something which could cause mass frustration when trying to fix. There are ways to get around this, see Help:Fixing templates for more details.

Nobody special

The template Template:Nobody special works on the same principles, with an extra few tricks included.

The template contains:

{{ucfirst:{{{person}}}}} is not special.<noinclude> [[Category:Help templates]]</noinclude>

(Again, the functional part of the template is in bold.)

This is slightly more complex, but not too tricky. Let's have a look at it.

  • The template takes a parameter {{{person}}},
  • Applies some function to it,
  • Puts it into the sentence, and finally,
  • Prints the sentence.

Now, what is {{ucfirst:}}? Double curly brackets, {{}} traditionally represent a template, but they can also represent things called magic words. There are quite a number of these, which the interested reader may like to have a look at here.

NB: Not all magic words work - it depends on the version of MediaWiki the YPPedia is running. Currently it is running version 1.6; therefore the wiki will only understand magic words designated as 1.6 or smaller.

The {{ucfirst:}} magic word actually capitalises the first letter of its parameter. So here, it capitalises the first letter of whatever {{{person}}} turns out to be. Let's have a look at this in action. Again, the previous rules established above still apply.

Example User input User output
1 {{Nobody special|Hello.}} {{{person}}} is not special.
2 {{Nobody special|person=He}} He is not special.
3 {{Nobody special|person=he}} He is not special.
4 {{Nobody special|person=iMHoTeP}} IMHoTeP is not special.
5 {{Nobody special|person=[[attesmythe]]}} attesmythe is not special.
6 {{Nobody special|person=i}} I is not special.

In example number 5, the magic word tries to capitalise the character [. It does not skip to the first letter and capitalise that.

It is worth noting that, as in example 6, the wiki cannot change things to make grammar correct. It is possible to program grammar rules into a template, but requires a horrendous amount of complex template programming. Instead, the issue can be side-stepped; the template could just be changed to make it more functional.

Nobody special 2

The template Template:Nobody special 2 is like its predecessor, but can deal with more:

[[{{ucfirst:{{{person}}}}}]] {{{verb}}} not special.<noinclude> [[Category:Help templates]]</noinclude>

So, what does this template do?

  • It replaces {{{person}}} with what the user defined it as,
  • Capitalises the first letter,
  • Links to the article,
  • Puts it into the sentence,
  • Replaces {{{verb}}} with what the user defined it as,
  • Puts that into the sentence as well, and then
  • Prints the sentence.

This template requires two inputs, {{{person}}} and {{{verb}}}. It relies on the editor to be able to provide the intuition of using the correct conjugated verb.

This template doesn't do anything wildly different to the first one, but here's another table of inputs and outputs:

Example User input User output
1 {{Nobody special 2|Hello.}} [[{{{person}}}]] {{{verb}}} not special.
2 {{Nobody special 2|person=He}} He {{{verb}}} not special.
3 {{Nobody special 2|person=piplicus|verb=is}} Piplicus is not special.
4 {{Nobody special 2|person=piPLiCuS|verb=is}} PiPLiCuS is not special.
5 {{Nobody special 2|verb=am|person=attesmythe}} Attesmythe am not special.
6 {{Nobody special 2|verb=is}} [[{{{person}}}]] is not special.
7 {{Nobody special 2|person={{Nobody special|person=He}}}} He is not special. {{{verb}}} not special.

As seen in example number 7, template can itself be defined as a parameter.

But isn't it a pain to have to define the verb each time, only because of the exceptions?

Parameter defaults to the rescue!

Parameters such as {{{verb}}} can be programmed such that:

  • It returns the value of {{{verb}}} if it was defined, or
  • It returns some other value if {{{verb}}} was not defined.

These are called parameter defaults.

Parameter defaults are defined as such:

{{{parameter|DEFAULT}}} where DEFAULT is the default value required.

Let's see it in action.

[[{{ucfirst:{{{person|someone}}}}}]] {{{verb|is}}} not special.<noinclude> [[Category:Help templates]]</noinclude>

What does this one do?

  • It checks to see if the parameter {{{person}}} is defined:
    • If it is defined, it replaces {{{person}}} with what it was defined as, capitalises the first letter, and then links to it;
    • It it is not defined, it replaces {{{person}}} with the word someone, capitalises the first letter, and then links to it.
  • It then checks to see if the parameter {{{verb}}} is defined:
    • If it is defined, it replaces {{{verb}}} with whatever it has been defined as, and then puts it into the sentence.
    • If it is not defined, it replaces {{{verb}}} with the word is, and then puts it into the sentence.
  • It then prints the sentence out.

The result of this table would be just the same as the above table, except {{{person}}} would be replaced with someone and {{{verb}}} with is.

Parameter defaults have a lot of uses. Here's another one.

Using parameter defaults to let a variable be defined by more than one word

It sure is a pain to have to write out person= and verb= when it's quite obvious that the first word is the subject and the verb is, well, the verb.

Take a look at Template:Nobody special 4 which contains the following:

[[{{ucfirst:{{{1|{{{person|someone}}}}}}}}]] {{{2|{{{verb|is}}}}}} not special.<noinclude> [[Category:Help templates]]</noinclude>

The functional part is bolded.

That's quite a lot of curly brackets. Let's break it up using some spaces:

[[{{ucfirst: {{{1| {{{person|someone}}} }}} }}]] {{{2| {{{verb|is}}} }}} not special.

That might make it more obvious what this template is trying to do. It does the same job as Template:Nobody special 3, except it'll now accept inputs of 1=parameter or just parameter. Let's examine the train of thought:

  • The template checks for a parameter 1=xyz or just xyz
    • If it finds it, it substitutes xyz (or whatever the value is) into the sentence, capitalises the first letter, and then links to it.
    • If it doesn't, it will check for a parameter person=xyz:
      • If it finds it, it will substitute xyz into the sentence and do the usual stuff.
      • If it doesn't, it'll use the default value of someone.

The template will then do the same for the second part, that is:

  • Check for 2:
    • If defined, use it
    • If not, check for verb
      • If defined, use that
      • If not defined, use default value of is.
  • Whatever is used, put it into the sentence

And then finally

  • Prints the sentence.

This template allows the user to be more lazy. It's useful when there's relatively few parameters, but should be avoided in complex templates, where it's useful to know what part is what.

Sometimes simpler is best

For example, take a look at Template:Nobody special 5. That's a lot of variables.

{{ucfirst:{{{person1|{{{1}}}}}}}}, the {{{adjective1|{{{2}}}}}} {{{job|{{{3}}}}}} who is most definitely not special, {{{verb1|{{{4}}}}}} {{{person2|{{{5}}}}}} in the {{{place|{{{6}}}}}}, and {{{action|{{{7}}}}}} because {{{person3|{{{8}}}}}} said that {{{reason|{{{9}}}}}}.<noinclude> [[Category:Help templates]]</noinclude>

Although {{Nobody special 5|piplicus|merciless|warmongerer|rumbled|Cleaver|palace|cheated|Lizthegrey|Cleaver needed a lesson taught to him}} would yield the perfectly valid sentence:

Piplicus, the merciless warmongerer who is most definitely not special, rumbled Cleaver in the palace, and cheated because Lizthegrey said that Cleaver needed a lesson taught to him.

if somebody needed to quickly change, say, the action, they'd have to look closely through the list.

Instead, this would make it much more easy to see what is going on:

{{Nobody special 5
|person=piplicus
|adjective=merciless
|job=warmongerer
|verb1=rumbled
|person2=Cleaver
|place=palace
|action=cheated
|person3=Lizthegrey
|reason=Cleaver needed a lesson taught to him
}}

If someone were to ask someone new to templates to edit that, they wouldn't have that much of a problem figuring it out - yet it still yields the same result.

Fancier template designs

So far, we've seen some pretty simple templates. More complex templates can be created that do much more spectacular things with just the same basic inputs.

The need for standardisation

The YPPedia has quite a lot of systematic naming schemes - islands, portraits, avatars - just to name a few.

One of the reasons for a precise yet simple way of nomenclature is that it doesn't take much intelligence to work out something unknown.

If a portrait of Barrister can be found at Image:Pirates-Barrister.jpg, where can an image of Eurydice can be found?

Easy! Image:Pirates-Eurydice.jpg

Let's find out if this is the case:

Pirates-Eurydice.jpg

It is! A template could be set up to generate a picture of someone when needed.

Template:Generate portrait contains the following text:

[[Image:Pirates-{{{1|{{{pirate}}}}}}.jpg|{{{alignment|right}}}|thumb|{{{size|}}}|{{{comment|}}}]]<noinclude> [[Category:Help templates]]</noinclude>

So, what does this do?

  • It checks for a value of 1= or pirate=
    • If it finds it, it'll produce the portrait image of the pirate in a thumb,
    • If it doesn't, the template will fail.
  • It then sets the picture with the following features, unless they're changed:
    • It will set the alignment to the right unless told not to.
    • It will generate the dimensions to be the normal width and height unless told otherwise.
    • It will print no comment unless told what to.

This allows such simple code such as {{Generate portrait|Eurydice}} to do its job, whereas if more specifics are needed, they can be added in: {{Generate portrait|Nemo|size=100px|alignment=left|comment=''Nemo'' could be named after the ''nemo whisk'', as opposed to ''Captain Nemo'' or ''Finding Nemo''.}}

Just to check these two templates actually work:

Pirates-Eurydice.jpg
Nemo could be named after the nemo whisk, as opposed to Captain Nemo or Finding Nemo.


Joys! They do.

Templates within templates

Templates can be nested within other templates. An example of this was seen earlier, with the template Template:Nobody special. A template within a template has limited use:

{{Nothing special|{{Nobody special|person={{Nobody special 2|person={{Nobody special 3|person=Hypnos}}|verb=is}}}}}} while looking all fancy, yields this:


[[Hypnos is not special.]] is not special. is not special.

Wouldn't it be neat if a lot of content could be changed by just a simple parameter? Luckily they can.

Parameter defining a template

The template for handling pirate infoboxes, Template:Infobox pirate, looks very complex. It is. Here is just a one-line selection of it:

{{Infobox pirate/portrait/{{{portrait|no}}}|piratename={{{altname|{{PAGENAME}}}}}}}

Let's have a look at what that does.

  • It checks for the value {{{portrait}}}
    • If it is defined, it plugs whatever that word is (expected to be the letters yes into the template,
    • If it isn't, it plugs in the value no.
  • It then checks for a value of altname
    • If defined, it uses that value
    • If not defined (as in the large number of cases), it uses the magic word {{PAGENAME}} to grab the name of the pirate needed - since an infobox containing information about Clio is only going to appear (we hope!) on Clio, it makes sense to grab the name of the page instead of having to type in some input of |pirate=Clio. All it does is save effort
  • Whatever value is used, it assigns it as the parameter piratename. This bit is the most subtle yet crucial part of the template.
  • The template then calls one of the following two templates:

If portrait was defined as no, it will write the following:

<div style="border:1px solid gray; margin-bottom:3px; background:white;">[[Image:portraitempty.png|{{{piratename}}} has no portrait]]</div>

What does this do?

  • It generates the image Image:portraitempty.png, which can be seen on the right:
Portraitempty.png
  • It then puts alternate text (text that comes up if the image fails to load, or text that can be seen when mousing over the image), which contains the text {{{piratename}}} has no portrait, where piratename was defined as the name of the pirate.
  • It then uses div tags to put a 1 pixel solid gray border around it (among other things)

So in short, if the user said they had no portrait, it shows the default blank portrait.

But what if they did have a portrait?

<div style="border:1px solid gray; margin-bottom:3px; background:white;">[[Image:Pirates-{{{piratename}}}.jpg|{{{piratename}}}]]</div>

will:

  • Display the portrait of the pirate (as, remember, due to systematic naming, we know where to find the portrait image of any pirate,
  • Display alt text of the name of the pirate.



It looked complex, but was very logical.

If you've understood that, then - congratulations, you understand almost everything there is to do with templates! If not, then don't worry - keep coming back to it. It's not easy at first to understand.

Redefining parameters

When a parameter is defined, it will only work for the template it is being used in. If the template has a template nested within it, a parameter defined in the first template will not work for the subtemplate.

Instead, they must be redefined.

In the previous template, we'll assume that the user does have a portrait, and has defined the variable altname. This means the template will look like this:

{{Infobox pirate/portrait/yes|piratename=altname}}

The bolded bit is the crucial part. If that was missed out, it would not work. Even if the template contained the following text:

[[Image:Pirates-{{{altname}}}.jpg|{{{altname}}}]]

It would not work, because the system does not know that the parameter altname or piratename is. It has to be defined in the template it is going to be used in each time.

Golden rules

Here are some golden rules for making templates:

If it works, it works

Templates are very versatile. Complex templates will involve picking text off of other templates, like with the infobox above. When creating a big template, the creator must think cleverly to make the template work, but make it as simple and efficient as can be.

The most important thing to remember is that a working template is better than a non-existent template. They can always be tidied up later

Choose the right way

Quite often, there's more than one way to design a template. The best way is normally the one that makes it the simplest for a user to use a template, by either taking less writing, is the least finicky about inputs, and tells the user where they've gone wrong if they have done. Don't worry too much if the code looks ugly behind the scenes. However, good templates often have quite clean code. Remember, if it works, it works, and that's better than a template that doesn't work.