More languages and units with AJAX

Submitted by Nicola Rainiero on 2012-11-21

An interesting feature for my future Storm Sewer software will be the ability to change and add new languages, simply clicking on a selector and editing a text file. In a similar way it can be the same with the units of measurement (for example changing the flow from m3/s to litre/s). I will show you my achieved results using AJAX and XML.

Well, at this moment they are incomplete and I found a bug: after I added new HTML code to DOM, this doesn't be translated!! But I'm going to improve my skills in Javascript and if I create functions and callbacks, I think that it will possibile to remove this inconvenient.

In this short article I will describe how I analyzed the problem and I will publish the used code. You can see the demo here.


My main reference is this tutorial: How to make your site Multilingual using XML and jQuery and I have adapted it to the following operations:

  1. read the url looking for a language variable (i.e. url?language=language_prefix) and definition of the language internal variable, if it doesn't exist this becomes English (en);
  2. from the reading of language.xml file, it builds items adding them in the selector button of the language, and changes the default language variable, if you select another language;
  3. search in XML file of all the ID and change the text inside the homonym CSS class in the DOM with the current language.

Here is my language.xml:

<?xml version="1.0" encoding="UTF-8"?>
<language value="en">English</language>
<language value ="it">Italiano</language>
<translation id="lang_title">
<en>Storm sewer web-app by Nicola Rainiero /-- --\</en>
<it>Fognatura bianca web-app di Nicola Rainiero /-- --\</it>
<translation id="lang_change">
<en>Change the language</en>
<it>Cambia lingua</it>
<translation id="units_change">
<en>Change the default units of measurements</en>
<it>Cambia le unità di misura</it>
<translation id="length">
<en>length </en>
<it>lunghezza </it>
<translation id="lang_method">
<en>Linear method</en>
<it>Metodo dell'invaso</it>

While here is my jQuery code:

// jquery for populate select of languages
// check if exist a language variable in url
if( {
language =; // query string exists
} else {
language = 'en'; // no query string exists
} // end if
// read language.xml and put all the existent languages
type: "GET",
url: "language.xml",
dataType: "xml",
success: function(xml) {
var select = $('#language');
var value = $(this).attr("value");
var title = $(this).text();
if (value == language) {
select.append('<option value="'+ value +'" selected=\"selected\">'+title+'</option>');
} else {
select.append('<option value="'+ value +'">'+title+'</option>');
}); // end language
}); // end languages
// function to change the default language
function displayVals() {
var singleValues = $('#language').val();
var language = singleValues;
var url=('http://' + window.location.hostname + window.location.pathname + '?language=' + language);
} // end function
// translation of all id starting with lang_
var id = $(this).attr('id');
var text = $(this).find(language).text();
$("." + id).html(text);
}); // end function
} // end functio(xml)
}); // end ajax
}); // end jquery

Units of measurement

In this case the International System of Units (i.e. SI) is the default system, the others will describe with a factor of conversion, for example if I define another system with the unit of length in km, then this ratio becomes 0.001 (because 1 m = 0.001 km).

The code ran the following operations:

  1. from the reading of measurement.xml file, it builds items adding them in the selector button of the units, and changes the default variable, if you select another units of measurements;
  2. initialization of all numerical arrays (according to what I read in this discussion), these arrays contain the values defined in specific CSS classes (for example the length is lnumber);
  3. conversion of all numeric descriptors through a moltiplication of the specific ratio and change of the unit label described by a CSS class (for example the length unit is lunit).

Here is my measurement.xml:

<?xml version="1.0" encoding="UTF-8"?>
<measurement value="m_mq_mc">m_mq_mc</measurement>
<measurement value="km_ha_l">km_ha_l</measurement>
<unit id="length">
<m_mq_mc value="m">1</m_mq_mc>
<km_ha_l value="km">0.001</km_ha_l>
<unit id="surface">
<m_mq_mc value="m&lt;sup&gt;2&lt;/sup&gt;">1</m_mq_mc>
<km_ha_l value="ha">0.0001</km_ha_l>
<unit id="flow">
<m_mq_mc value="m&lt;sup&gt;3&lt;/sup&gt;/s">1</m_mq_mc>
<km_ha_l value="l/s">1000</km_ha_l>

While here is my jQuery code:

// jquery for populate select of measurements
// read measurement.xml and put all the existent units
type: "GET",
url: "measurement.xml",
dataType: "xml",
success: function(xml) {
// read xml units id to populate option START
var select = $('#unit');
var value = $(this).text();
if (typeof def_unit === 'undefined') {
def_unit = 'm_mq_mc';
if (value == def_unit) {
select.append('<option value="'+ value +'" selected=\"selected\">'+value+'</option>');
} else {
select.append('<option value="'+ value +'">'+value+'</option>');
}); // end measurement
}); // end xml measurements
// read xml units id to populate option END
// end option reading
// change the selected units of measurement START
$('#unit').change(function() {
var id = $(this).children(":selected").attr("value"); // id = m_mq_mc, etc.
def_unit = id;
// ... convert the measures START
if (typeof Lnumber === 'undefined') { // initialize the array wthin length and other measures
Lnumber = $('html').find('.lnumber').map(function() { return $(this).text(); }).get();
// can follow new arrays for other class: surface, flow, etc.
} // end if
$(xml).find('unit').each(function(){ // read XML with the selected id = m_mq_mc, etc.
var id = $(this).attr('id');
var value = $(this).find(def_unit).attr('value');
var text = $(this).find(def_unit).text();
// a test with lnumber class = length number format
if (id == 'length') {
ratio = parseFloat(text);
var convert = Lnumber[indice] * ratio;
}); // end function lnumber
// a test with lunit class = unit of measurement format
if (id == 'length') {
}); // end function lunit
}); // end function unit
// ... convert the measures END
}); // end function unit
// change the selected units of measurement END
} // end xml
}); // end ajax
}); // end jquery

At this moment my solution is a little complicated, but I hope to improve and simplified it.

If you want to see the demo click here, while I put all files here: As usual I accept with pleasure any help, hint, correction, and so on!!!

Related Content:

Nicola Rainiero

A civil geotechnical engineer with the ambition to facilitate own work with free software for a knowledge and collective sharing. Also, I deal with green energy and in particular shallow geothermal energy. I have always been involved in web design and 3D modelling.