filter generico

From MoodleDocs

Using Generico (and Video Easy)

Introduction

In technical terms Generico and Video Easy are filters for Moodle. But that doesn't go very far towards describing how they can help you. In user speak, they allow an administrator to define reusable snippets of html/css and javascript that can be popped into Moodle html areas. These snippets are called templates. Simple templates can be used to display a welcome message with the current logged in user's name, an attractive green button that returns users to the main course page, a video player or an FAQ style accordion. More advanced templates have been used to make QR codes, text to speech widgets and image slideshows.

Whats so good about this? Well it gives you considerable ability to customize your Moodle site without having to resort to multiple plugins, or custom PHP coding. It also allows you to centralise and reuse common bits of html, such as disclaimers and copyright notices. Finally it provides a way to allow your users to perform tasks such as the embedding of iframe content from a specific site, without needing to give them permission to embed iframes generally.

Writing templates requires as much skill as the complexity of the template. But using templates that have already been made requires no particular skill at all. Both Generico and VideoEasy come with a collection of pre-made templates to help you get started.

Whats the difference between Generico and VideoEasy?

They are very similar and from a template makers point of view are almost the same thing. Where they differ mainly is how and when Moodle chooses to apply a template to an HTML page, and how variables are passed to the template.

VideoEasy

VideoEasy works by looking for html links on the page. If the html link matches a file extension VideoEasy is registered for, it will replace the link with the processed template.

So a link to a video file with an .mp4 extension, could be replaced by an mp4 video player. Despite its name, VideoEasy is not limited to video at all. it is possible to register other file extensions too. For example, it is possible to register the .pdf extension and replace .pdf links with a pdf viewer.

File extensions that VideoEasy should handle are registered at: Site Administration -> Plugins -> Filters -> Video Easy -> General Settings

The actual template that should be used for a file extension is registered on the same page. This can be overridden at the course or activity level via the “settings” button on the “filter” page accessed from the activity instance's settings menu. This allows different courses or activities to use different video players if necessary.

Variables can be passed to the template by appending parameters to the html link URL. So in the url http://mysite.com?favoritefruit=apple, the variable 'favoritefruit' will be populated with the value 'apple' and made available to the template as @@favoritefruit@@.

Generico

Generico works a little differently to VideoEasy. Rather than act on links in the text area, it acts on specially formatted text blocks that look like this: {GENERICO:type="greenbutton",text="Go Back"}

When it finds one of these, it replaces it with the processed template. A template author might be able to make these crafty little text blocks by hand, but it is not realistic for average users. So a special plugin is available for the Atto text editor which can prepare the Generico filter strings for the user.

Using a Generico template

There are two ways you might add a Generico template to a page.

i) Manually enter a Generico filter string on a page
ii) Selecting a Generico template from the Generico popup dialog on the Atto text editor.

In most cases you will use the latter, because it is simple and less prone to human error. Lets look at the example of a Generico template to display a pretty button with custom caption and link. In such a case the Generico filter if added by hand would look like this: {GENERICO:type=prettybutton,caption="Generico goes to Google",link="http://www.google.com"}

If however you used the Atto popup dialog, it would look like this first:

attopopup.png

But even after you have used the Atto Generico plugin to insert your Generico string on the page, it is still just a Generico string. It doesn't look anything like a button. This is because Generico processes the filter string only after the html area content is saved, and the page containing it is displayed.

The reason we call Generico templates … “templates” is that they are combined with some data to produce the final html snippet that is displayed on the page. In the case of the pretty button, this data was the caption and the url. When the template is created, placeholders called variables are inserted into it. Then when you add the template to a page you pass in the data, e.g. caption and url, and they will be merged with the template to create the html snippet. The Generico Atto text editor plugin will generate a simple form with a field (i.e. text area or dropdown list) for each variable to make it easier for the user.

Examining a simple Generico Template

So lets make a simple Generico template. Templates are defined in the site administration area. Each template will have an entry under: site administration->plugins->filters->generico

By default there are 20 blank templates when Generico is installed, but it is possible to add more. Blank Generico templates do nothing, you have to fill them in before anything will happen. But its easy enough to make a new template that does something, because there are preset templates that can be used. Lets use the simplest one of all the “hello world” template. To do this: i) open a blank template ii) from the first control on the template settings page, choose “hello world” from the dropdown list of template presets. iii) Scroll to the bottom and save the template. That's it, the template is created. Type the filter string “{GENERICO:type=helloworld}” into an html area (try a forum post or a page resource), Or choose/insert the filter string from the Generico atto editor plugin. When the page is displayed there should be a message saying “hello world [yourname].”

So what actually happened there? Well it goes like this....

a) Moodle is sending the page to the browser
b) It looks through the page for any Generico filter strings, and when it finds one:
 i) it removes the filter string from the output
 ii) it processes the filter string and replaces it with the processed output.
c) it sends the output to the page

The processing involves looking for variable placeholders in the template, and matching those with data in the filter string. When they match, variable placeholders in the template are swapped out for the filter string data. Then the processed template is returned to the browser. This behaviour is explained in more detail later.

Importing and Exporting Templates

To allow you to share templates that you or others have created, it is possible to import and export them. On the top right of a template's settings page, there is a green box titled “Bundle.” Clicking on the box will export the template to a text file of the same name as the template key. So for template “helloworld,” a hello world.txt file will be exported and the download begin immediately. To import such a file, you drag the text file onto the green bundle box. The border will turn blue. When the file is dragged and dropped there, the currently loaded template will be overwritten or filled in, with the imported content. The changes are not permanent however until the template is saved. So you will need to scroll to the bottom of the page and press the save button.


The Template Fields

The settings page for each template has X fields for Video Easy and 14 for Generico. The order and naming are a little different also. We can think of each field as being in one of 4 categories: General, HTML, Javascript and CSS. In the case of the hello world template there is no javascript or CSS. We just return some html. But we could add some CSS styles or even a javascript click event to the text if we wanted to. Lets look at each field in turn

a) The Template Key
b) The Template Name
c) The Template Instructions 
d) The Template Body
e) The Template Body End
f) The Template AMD flag
g) The Template JQuery flag
h) The Template Require JS 
i) The Template Script 
j) The Template Upload JS
k) The Template Require CSS
l) The Template CSS
m) The Template Upload CSS
n) The Template Dataset
o) The Template Dataset Datavars
    

The Template Key

The template key is a unique identifier that is used in internal processing and is the most important part of a Generico filter string. The key should not contain any spaces or non alphanumeric characters(underscores are ok). The key is the “type” part of the Generico filter string. e.g. in the prettybutton example we used earlier, the template key would be “pretty button.” {GENERICO:type=prettybutton,caption="Go to Google",link="http://google.com"}

All other parts of the template you can change and the behaviour will change accordingly when the template is processed. But if the key is changed, all the filter strings that are live on the site for that template will no longer be processed. That is because the “type” will not be matched with any template's key.

The Template Name

The template name is simply what is displayed around the site when referring to the template. i.e. on the settings pages and in the Atto text editor. Unlike the “key” you can include spaces and non alpha numeric characters here.

The Template Instructions

The template instructions will be displayed on the Atto text editor Generico insert form for the template. There is not much space there, so short instructions are best.

The Template Body

The template body is where you put any html that should be put on the page in place of the Generico filter string that is being processed. In the case of the “helloworld” example the template body looks like this: Hello World @@USER:firstname@@

Note the use of a variable, in this case a preset variable that will return the current user's first name. But the important thing here is that the actual replacement of the generic filter string takes place here. Whatever is in the body section will replace the string, albeit with any variables replaced by their actual value.

The Template Ends Section

This is only present for Generico. This will be processed in place of the “Template Body” section if the filter string's type attribute is of the format ’type=[key]_end’ e.g. {GENERICO:type=helloworld_end}. This is designed for use in the case where a template requires opening and closing tags. Lets take an example of a lightbox template that shows an image in a lightbox when a button was pressed. Two generico filter strings would be placed on the page, one for the opening tags, and another for the closing tags. So it might look like this: {GENERICO:type=lightbox} {GENERICO:type=lightbox_end}

The user could then insert an image between them using the standard Moodle “insert image” icon on the editor. The Generico Atto plugin is aware of the Template end field, and if it is not blank will automatically insert the end filter string on the page along with the main filter string.

The Template AMD flag

AMD is a javascript loading system that was put in place in Moodle in version 2.9. AMD loads any javascript dependencies for your template safely, and prevents naming and version conflicts with the dependencies of other templates and javascript on the same page. If your template does not involve javascript or its older than Moodle 2.9, then you won't need to worry about this. If you do use javascript in the “template script” area (described later) then setting AMD to “yes” will make jQuery available to your script. If you load 3rd party libraries in the “template require JS” or “template upload JS” area you might have to choose whatever the 3rd party library recommends. A library that supports AMD will generally fail if you do not select “yes.” A library which does not support AMD will usually fail if you select “yes.”


The Template JQuery flag

When a third party library you load, or your own script, relies on JQuery you can force it to be loaded by setting this to “yes.” But you really should never do this. If you can find another way, then that would be better. (Warning: techy explanation follows) The reason for this, is that jQuery has versions and plugins. If another template or something else on the page has loaded a jQuery plugin, or requires a different version of jQuery, when you force load jQuery you will overwrite any jQuery (and plugins) that something else has already loaded. That something else will then fail. These conflicts can be hard to track down and are the very thing that the AMD system was designed to avoid. If you really need jQuery, and you can't use AMD, try to use a theme that loads jQuery. Most of the nice themes like Essential do. Failing that, in the additional HTML area of moodle in the “HEAD” section, add your jQuery call. (Note that even loading jQuery using the additional HTML section of Moodle, you risk causing problems with other plugins that require jQuery.)

Devs here might wonder why Generico and VideoEasy don't just use load jQuery using the $PAGE requirements manager in PHP. The problem is that the filter is often called after the page header has already been sent out to the browser. Trying to require jQuery via the $PAGE requirements manager at that point will cause an error.

The Template Require JS

If your template requires a 3rd party library, such as a library for making light boxes, then you can place the url for the library here. This is useful when the library makes itself available via a CDN (content distribution network). Because there is not requirement to supply the library itself with the template, just the URL, many presets and Generico/VideoEasy bundles load 3rd party libraries in this way.

When specifying the library's URL, start with // (i.e. not https: or http:).

The Template Script

The template script if specified will be called once for each of your template's filter strings on the page. It is common to use this to set up any event handlers or any DOM manipulation you need to do to init your template. For example, if you are placing a button on the page that will open an image in a lightbox, you would add the html for the button in the “template body” and attach the event handler for the click event here. In this case you will generally need to give the button a class or an id attribute, and then select the element for that class or id in the script area. This is because the script is executed only after all the html has loaded on the page. To make it easy to use the same id or class in the “template script” and “template body” areas a special variable AUTOID is made available. This will provide a random and hopefully unique string that can be used as an element's id or class, and that will be the same throughout the processing of a particular filter string.

Now at this point we really need to talk about variables. In your template you can use variables of your own definition, or you can use preset variables. AUTOID and USER:firstname are two examples of preset variables. Generico/VideoEasy will ensure they contain the correct data. You can declare your own custom variables too. Anything surrounded by double @@ marks will be treated as a variable. So in your template @@AUTOID@@ and @@FAVORITECOLOR@@ would be recognised as variables. If its a custom variable Generico will get the value from the filter string. VideoEasy will get custom variables’ values from the URL parameters. It is also possible to set default values for Generico/VideoEasy so that if not specified the default value will be used.

There is an important thing to note about using variables. Variables can be used in the “template body” and “template script” areas. But the processing is a little different. In the template body the variable @@FAVORITECOLOR@@ might be replaced by ‘pink.’ But in the template script it will be replaced by ‘opts[‘FAVORITECOLOR’].’

So in the “template body” you can place variables any way you choose and they will be swapped straight out for the value. But in “template script” you have to be careful NOT to write something like this: var elem = $(‘#@@AUTOID@@’);

this will fail because post processing it will look like this: var elem = $(‘#opts[‘AUTOID’]’);

Instead you should write this: var elem = $(‘#’ + @@AUTOID@@);

This will work and will lead to something like this: var elem = $(‘#’ + opts[‘AUTOID’]);

You might be wondering why we have to do it this way for the script. The reason is that the script file will be cached be Moodle. By using the opts variable in place of the literal value of the variable, caching will work nicely and the user will never be served up old content (or someone else's content).


The Template Upload JS

The upload js area allows the administrator to upload a javascript file that will be loaded in the same way that the “template require js” file is loaded. It can be used in addition to the template require js file and is useful when you need more than one 3rd party library file, or when you want the javascript file loaded from the Moodle server and not from a CDN or other internet source.

The Template Require CSS

If your template requires a 3rd party CSS file, then you can place the url for the library here. When specifying the library's URL, start with // (i.e. not https: or http:).

The Template CSS

Specify any custom CSS for your template here. Unfortunately you cannot use template variables in the custom css area. The custom CSS is loaded quite late and the late application of styles is noticeable by the user. If this is a concern, save your custom css declarations to a file and upload them into the “template upload CSS” area.

The Template Upload CSS

Similar to the “Template upload js” area, the “Template upload css” area allows the template author to upload a 3rd party CSS file. This is useful when the file should be accessed from the local server, or when the CSS styles should be applied earlier than those specified in “custom css” are.

The Template Dataset

It is also possible to set a custom SQL script which will be executed server side and the resulting data returned to your template. The SQL script will be called using Moodle's $DB->get_records_sql() function. See: https://docs.moodle.org/dev/Data_manipulation_API#moodle_database::get_records_sql.28.29

If there is only a single record returned, the record will be available for use in the body area of the template using the following syntax @@DATASET:[fieldname]@@. e.g. template dataset: “SELECT * FROM {user} WHERE id = 37;” template body: User 37’s first name is @@DATASET:firstname@@, don’t forget it.

Whether one record or many are returned, if you specify a dataset then a @@DATASET@@ variable will be available to your template's custom javascript. This will be an array of objects, each object representing one of the records that were returned. In the process of conversion from a PHP array of objects to an javascript array of objects, the order/index of the objects in the array appears to be modified, and so cannot be relied upon.

The Template Dataset Variables

Template variables do not work in the template dataset. This is because the get_records_sql api has its own template system. The first parameter to the function is the SQL statement. When you place question marks in the SQL statement, i.e. ‘?’ , Moodle recognises that as a variable. Variable values are passed in the second parameter to the function. Moodle will swap out each question mark for one of the values passed in the second parameter. Generic uses this system and allows you to specify a comma separated list of variable values in the Template Dataset Variables field. You can specify Generico template variables here, which gives this a lot of power. Lets demonstrate this by rewriting the above example to return the currently logged in user's information.

template dataset: “SELECT * FROM {user} WHERE id = ?;”

template dataset vars: @@USER:id@@

template body: User @@USER:id@@’s first name is @@DATASET:firstname@@, don’t forget it.


Actually this is trivial because we already have access to the currently logged in user's information via the Generico @@USER:xx@@ variable. But it demonstrates how to pull a dataset from the database using Generico template variables. You can use @@USER:xx@@, @@COURSE:xx@@ or any of the preset variables, and in addition can use variables which you have defined yourself.

If there is more than one record returned from the get_records_sql call, then you won't be able to access @@DATASET:xx@@ to get the field. In that case @@DATASET@@ will contain an array of objects and will only really be useful in the custom js area. Each object will represent a record from the dataset. The indexes on the array will likely be the ids of the records returned, so you won't be able to get the first record with @@DATASET@@[0].

Note that there are no ajax calls to get the data. When the filter is parsed the data will be fetched, and after that it will not be fetched again.

NB A bug in the current implementation of Generico means that only the first of the set of variables specified in the Dataset variables is actually made available to the plugin.

Native Variables

Generico and Video Easy provide a number of variables that can be used out of the box. They should be surrounded by double @ marks in order to be recognised. e.g. @@AUTOID@@ or @@USER:firstname@

Common Native Variables

There is only one of these. But its a good one, you will use it a lot.

AUTOID = An auto generated id to use in the container div or elsewhere.

This is used to give a unique id to html elements, that can then be found from javascript. The value of AUTOID will be different each time the filter is run, but will be the same for each field in the template.

Generico Native Variables

USER:xxxx =A value from the current user's user record. xxxx= the field of the user record

COURSE:xxxx A value from the current course record. xxxx= the field of the course record

WWWROOT = The url of the moodle site

MOODLEPAGEID = The value of the id parameter passed into the url of the current page(if present)

URLPARAM:xxxx = The value of a url param passed into the current page. xxxx= the url param. For videoeasy, url params are available as top level native variables, without the URLPARAM: bit.

Video Easy Native Variables

FILENAME = filename of video

AUTOJPGFILENAME = the video filename but with a jpg extension

AUTOMIME = video file mime type determined by file extension

AUTOPNGFILENAME = the video filename but with a png extension

AUTOPOSTERURLJPG = the full video url but with a jpg extension

AUTOPOSTERURLPNG = the full video url but with a png extension

CSSLINK = used internally to load a CSS file if needed

DEFAULTPOSTERURL = url to a default poster image. VideoEasy ships with bland grey image. But you can upload your own default poster image on the Video Easy general settings page.

FILEEXT = The file extension of the video file

VIDEOURL = the url of the video

URLSTUB = the url of the video minus the file extension

PLAYER = the type of player (videojs, flowplayer ...etc.)

TITLE = the video title (from linked text)

WIDTH = the width of video

HEIGHT = the height of video