Location: PHPKode > scripts > Universal Language Tool for PHP > universal-language-tool-for-php/index.php
<?php

if ($HTTP_POST_VARS) {
  foreach(array_keys($HTTP_POST_VARS) as $Var) {
   $$Var=$HTTP_POST_VARS[$Var];
  };
};

if ($HTTP_GET_VARS) {
  foreach(array_keys($HTTP_GET_VARS) as $Var) {
    $$Var=$HTTP_GET_VARS[$Var];
  };
};

  include_once('ult.php'); // Universal Language Tools
//  include_once('urlt.php');  // URL tool

if (! $lang) $lang = 'en';

$dvl = new ULT;
$dvl->set_source_language ('en');
$dvl->set_display_language ($lang);

$dvl->block_start();
  
?>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
"http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<title>ULT - Universal Language Tool for PHP</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link href="main.css" rel="stylesheet" type="text/css">
<style type="text/css">
<!--
.style1 {font-family: "Courier New", Courier, mono}
-->
</style>
</head>

<body>
<table width="780" border="0" align="center" cellpadding="0" cellspacing="0">
<!--
<tr>
<td class="languages"><p>
<?php 
foreach ($lang_defs as $m_lang) {
  $m_lang_name = $m_lang['name'];
  $m_lang_id = $m_lang['id'];
?>
<a href="index.php?lang=<?php echo $m_lang_id ?>"><?php echo $m_lang_name ?></a>&nbsp;&nbsp;&nbsp;
<?php 
  $m_lang = $lang_defs[$lang];  
}

?>
</p></td>
</tr>
-->
<tr>
<td><h1>##Universal Language Tool for PHP##</h1></td>
</tr>
<tr>
<td><span class="subtitle"><a href="#recognizingproblem">Recognizing the problem</a> * <a href="#thesolution">The solution</a> * <a href="#realization">Realization</a> * <a href="#languagedefinitions">Language definitions</a> *<a href="#languagedictionaries"> Language dictionaries</a> * <a href="#transliteration">Transliteration</a> * <a href="#languagefamilies">Language families</a> * <a href="#howtoprepare">How to prepare documents</a> * <a href="#propertiesandmethods">Properties and methods</a> * <a href="#howtouse">How to use library</a> * <a href="#download">Download</a> * <a href="http://www.datavoyage.net/oreska/index.php?c=6" target="forum">Support forum</a> *<a href="#contact">Contact</a></span></td>
</tr>
<tr>
<td>
<h2 class="subtitle"><a name="recognizingproblem"></a>What is ULT </h2>
<p>After looking for multilanguage solution we in DataVoyage realized that we need to write our own. Before you comment this as just another multi language support PHP library take a look for some specific usage this library offers. </p>
<p>Univeral Language Tool for PHP is library developed to introduce new concept in multilanguage application develipment for WEB. It offers functionality which covers unlimited number of languages on sigle site, but in literal manner. It does not support just widely recognized term of languages but also expands to support language variations. You are provided with tools to use language macros in your documents which are replaced with exact text according to language dictionaries. However, you also are provided with transliteration tool, which allows direct text replacament in document with no need for predefined macros. The replacement is done according to transliteration rules specific for each language. </p>
<p>If you ever developed site which is targeted to audience which uses the samelanguage but with some variations (example: english and american english, or variations of spanish language, or the same language that uses two scripts, like serbian latin and serbian cyrillic) you met this problem. Usual multilanguage solutions force you to treat all these variations as different languages, which makes nit just developmentbut administration and site update quite complicated tasks. ULT treats all variations as the same language but it introduces difference rules. This means you are entitled to update site in justone language, and if needed, ULT will alter original document to create its variation acording to predefined language variation rules. </p>
<h2 class="subtitle"><a name="recognizingproblem"></a>Recognizing the problem </h2>
<p>What is the goal we wanted to be accomplished? Well, most of the multi language libraries are basically simple. You have definitions for language macros for wanted languages, and loaded page knows which one to use to alter page contents. Libraries mostly differ in approaches but essence is the same. </p>
<p>We develop web sites for a long time, and since our clients are mostly in Serbia we are faced with multi language problem on many occasions. Surely we solved it in the same manner as described, but we always had problems with that way. </p>
<p>Serbian language presents specific problem  - the language may use two scripts cyrillic an latin. We usually treated this two scripts as two languages and got usable results but not satisfactory. Although two scripts do act as different languages, they are actually not. Differences among scripts are just that - different scripts are used, but everything else is the same (with some minor issues). It is against common sense to treat them as different languages, creating separate dictionaries or bitmap sets or whatever else on site is language dependable, just for minor differences. That would be a nightmare, not just to create but also to maintain.</p>
<p>Although serbian language is probably unique about using two scripts, other languages do have their variations, take a look at variations of english or spanish language. </p>
<p>After some thoughts we came to this conclusion: <strong>A language is complex and usually it has some variations, but those variations are different in minor ways and usually by following some definite rules and exceptions. Thus, we should not deal with language variations as language themselves, but as such - VARIATIONS of original language. </strong>This conclusion is basic idea for ULT.</p>
<p>We recognized two ways language variations may differ: by dictionary (some words, phrases or spelling differences) and by script (this may be literally as in serbian or simply by using different code pages). <a name="thesolution"></a></p>
<h2><span class="subtitle">The solution</span></h2>
<p>After trying several approaches we came to the final solution: to allow definition of language as such with one improvement - we allow language to be defined as child of another language. That allows us to have mechanism to provide basic language definitions and variations to them. </p>
<p>What the script does when language information is needed is to merge basic language with variation differences and thus produce complete language variation as new language. What we got is that you actually have to define and maintain just basic languages for your site and define variations through rules of differences. If you change something in definition of basic language it will reflect all it's variations. This means, if you have to define dictionary, you will have to do it just for basic language. Variation will only have definition for difference rules. </p>
<p>Let's se an example, english language for instance. </p>
<p>There are few differences among english and american english in words spelling. For instance, english word <em>colour</em> is spelled <em>color</em> in american english. ULT allows you to have both variations on your site but there is no need to define whole dictionaries for both. You will have english language fully defined and for american english you will state that it is child of english language with spelling differences for word <em>colour</em>. And that is all. Whenever your page is loaded in american english, dictionary of english language would be used but with variation differences applied. So, reultin document wil have all occurencies of word <em>colour</em> replaced with word <em>color.</em><a name="realization"></a></p>
<h2>Realization</h2>
<p>We have created ULT PHP class (stored in ult.php) which deals with the problem. It does most of the job automatically. Your job is to initialize object, set some parameters and of course define some languages. </p>
<p>Here is an simple example of it's usage. </p><table width="650" border="0" align="center" cellpadding="0" cellspacing="0">
<tr>
<td>
<p>##SOURCE_CODE## </p></td>
</tr>
</table><table width="650" border="1" align="center" cellpadding="0" cellspacing="0" bordercolor="#000000" bgcolor="#CCCCCC">
<tr>
<td>
<pre>&lt;?php

//this code deals with passing parameters


if ($HTTP_POST_VARS) {
 foreach(array_keys($HTTP_POST_VARS) as $Var) {
   $$Var=$HTTP_POST_VARS[$Var];
 };
};
 
if ($HTTP_GET_VARS) {
 foreach(array_keys($HTTP_GET_VARS) as $Var) {
   $$Var=$HTTP_GET_VARS[$Var];
 };
};
 
include_once('ult.php'); // include Universal Language Tool library in page code


// language id parameter is stored in $lang
// we have to initialize it if parameter value not passed
if (! $lang) $lang = 'en'; 


// create language object, this will also load all language
//definitions stored in -lang directory
$dvl = new ULT;


// now set source language (language that is used to design page)<br>// this is not necessary if you set [is_source_lng] property of rone of the language definitions
$dvl-&gt;set_source_language ('en');

// set display language (language that is actualy used on page)
$dvl-&gt;set_display_language ($lang);

// start output buffering. This must be done to allow multilanguage processing
$dvl-&gt;block_start();

?&gt;

&lt;!DOCTYPE HTML PUBLIC &quot;-//W3C//DTD HTML 4.01 Transitional//EN&quot;
&quot;http://www.w3.org/TR/html4/loose.dtd&quot;&gt;
&lt;html&gt;
&lt;head&gt;
&lt;title&gt;ULT Test&lt;/title&gt;
&lt;meta http-equiv=&quot;Content-Type&quot; content=&quot;text/html; charset=utf-8&quot;&gt;
&lt;/head&gt;
&lt;body&gt;
 
&lt;p&gt;
&lt;?php 
// this will diplay list of all languages whose definitions are loaded
foreach ($dvl-&gt;lang_defs as $m_lang)
  $m_lang_name = $m_lang['name'];
  $m_lang_id = $m_lang['id'];
  echo &quot;&lt;a href=\&quot;index.php?lang=$m_lang_id\&quot;&gt;$m_lang_name&lt;/a&gt; &quot;
  $m_lang = $dvl-&gt;lang_defs[$lang];
}
?&gt;
&lt;/p&gt;

<p>&lt;p&gt;# #LANGUAGE_TEST# #&lt;/p&gt;</p>&lt;p&gt;# #Language# #:&lt;?php echo &quot;$m_lang[name] ($lang)&quot; ?&gt;&lt;p&gt;

&lt;p&gt;# #Family# #: &lt;img src=&quot;img/lngpic=%en=.gif&quot; width=&quot;49&quot; height=&quot;12&quot;&gt;<br>
&lt;p&gt;# #OK# # # #CANCEL# # # #ABORT# # # #CONFIRM# # # #COLOUR# #&lt;p&gt;

<p>&lt;/body&gt;<br>&lt;/html&gt;<br>&lt;?php
$dvl-&gt;block_end()
?&gt;</p>
</pre>
</td>
</tr>
</table>
<a name="test"></a><br>
<table width="650" border="0" align="center" cellpadding="0" cellspacing="0">
<tr>
<td>
<p>##EXECUTION_RESULT## </p></td>
</tr>
</table>
<table width="650" border="1" align="center" cellpadding="20" cellspacing="0" bordercolor="#000000">
<tr>
<td>
<p>
<?php 
foreach ($dvl->lang_defs as $m_lang) {
  $m_lang_name = $m_lang['name'];
  $m_lang_id = $m_lang['id'];
  echo "<a href=\"index.php?lang=$m_lang_id#test\">$m_lang_name</a> ";
  $m_lang = $dvl->$lang_defs[$lang];  
}

?>
<p>##LANGUAGE_TEST## </p>
<p>##Language##:
<?php 
echo "$m_lang[name] ($lang)" ?>
</p>
<p>##Family##: <img src="img/lngpic=%25en=.gif" width="49" height="12"></p><p>##OK## ##CANCEL## ##ABORT## ##CONFIRM## ##COLOUR##</p>
</td>
</tr>
</table>
<a name="languagedefinitions"></a><h2>Language definitions </h2>
<p>Other than ult.php you need proper language definitions and language dictionaries created in language directory if you did not set library to load them from elsewhere. We provided some basic definitions for your start. </p>
<table width="650" border="0" align="center" cellpadding="0" cellspacing="0">
<tr>
<td>
<p>##LANGUAGE_DEFINITION##: ldef_en.php</p></td>
</tr>
</table>
<table width="650" border="1" align="center" cellpadding="0" cellspacing="0" bordercolor="#000000" bgcolor="#CCCCCC">
<tr>
<td>
<pre>&lt;?php<br>$lng_def['id'] = 'en';<br>$lng_def['name'] = 'english';<br>$lng_def['codepage'] = 'utf-8';<br>?&gt;
</pre></td>
</tr>
</table>
<p>Language definition is done by setting array named <strong>$lng_def</strong>.</p>
<p><strong>Property $lng_def['id'] </strong>contains language ID. It is recommended to use standard language IDs. Then, You may read default language from visitor's browser and set that language for display language. </p>
<p><strong>Property $lng_def['name'] </strong>contains name of the language. This name may be used to present language name in document.</p>
<p><strong>Property $lng_def['codepage'] </strong>contains standard sign for code page used for language. You may use it to set correct code page for document. This also may be used for code page conversions if you use different code page for child and parent languages. </p>
<p><strong>Property $lng_def['parent'] </strong>is used when you define child language. This property contains ID of parent language. </p>
<p><strong>Property $lng_def['is_source_lng'] </strong>contains 1 if language should be used as source language for the site.</p>
<p>Here is an example: </p><table width="650" border="0" align="center" cellpadding="0" cellspacing="0">
<tr>
<td>
<p>##LANGUAGE_DEFINITION##: ldef_en-us.php</p></td>
</tr>
</table>
<table width="650" border="1" align="center" cellpadding="0" cellspacing="0" bordercolor="#000000" bgcolor="#CCCCCC">
<tr>
<td>
<pre>&lt;?php<br>$lng_def['id'] = 'en-us';<br>$lng_def['name'] = 'english(us)';<br>$lng_def['codepage'] = 'utf-8';<br>$lng_def['parent'] = 'en';<br>?&gt;</pre></td>
</tr>
</table>
<p><strong>Property $lng_def['parent_conversion_table'] </strong>is used for setting language transliteration but this will be explained later. </p>
<p>There is language naming convention. It is consisted of prefix '<em>ldef_'</em> followed by language ID and extension <em>'.php'</em>. Prefix may be customized by altering value od constant named <em>LANG_DEF_FILE</em>.<a name="languagedictionaries"></a></p>
<h2>Language dictionaries</h2>
<p>Language definitions introduce available languages to the library. However, to use those languages you also need language dictionaries. Although definitions and libraries might be in the same file there is a good reason to separate them. This allows you to load dictionaries only for language used on single document and preserve resources. Also, usage of several dictionaries for the same language is recommended. There is no need to load whole large dictionary for simple page. It is better to divide dictionary in several parts and load only those which are really needed in a document. You may use function<em> add_dictionary ()</em> for this purpose. </p>
<p>Here is an example of dictionary for english language. </p>
<table width="650" border="0" align="center" cellpadding="0" cellspacing="0">
<tr>
<td>
<p>##LANGUAGE_DICTIONARY##: ldct_en.php</p></td>
</tr>
</table>
<table width="650" border="1" align="center" cellpadding="0" cellspacing="0" bordercolor="#000000" bgcolor="#CCCCCC">
<tr>
<td>
<pre>&lt;?php<br>$lng['OK']='OK';<br>$lng['CANCEL']='Cancel';<br>$lng['COLOUR']='Colour';<br>$lng['family']='family';<br>$lng['LANGUAGE_TEST']='LANGUAGE TEST';<br>$lng['Language']='Language';<br>$lng['ABORT']='Abort';<br>$lng['CONFIRM']='Confirm';<br>$lng['Universal Language Tool for PHP']='Universal Language Tool for PHP';<br>$lng['ULT']='ULT';<br>$lng['SOURCE_CODE']='SOURCE CODE';<br>$lng['EXECUTION_RESULT']='EXECUTION RESULT';<br>$lng['LANGUAGE_DEFINITION']='LANGUAGE DEFINITION';
$lng['LANGUAGE_DICTIONARY']='LANGUAGE DICTIONARY';
?&gt;</pre></td>
</tr>
</table>
<p>And an example of dictionary for variation of english language - american english. </p>
<table width="650" border="0" align="center" cellpadding="0" cellspacing="0">
<tr>
<td>
<p>##LANGUAGE_DICTIONARY##: ldct_en-us.php</p></td>
</tr>
</table>
<table width="650" border="1" align="center" cellpadding="0" cellspacing="0" bordercolor="#000000" bgcolor="#CCCCCC">
<tr>
<td>
<pre>&lt;?php<br>$lng['COLOUR']='Color';<br>?&gt;</pre></td>
</tr>
</table>
<p>Simple, isn't it? Variation contains just difference definition in dictionary. Library will load parent language first (which is, by definition, english language) and then apply dictionary for american english, which actually alters definition for <em>COLOUR</em> language macro. </p>
<p>As you can see, dictionary contains definition for<strong> $lng</strong> array. This is used to build in memory dictionary for specified language. You must put language macros in document to use dictionary. Macros are placed by putting macro name between double hash symbol, like <em>##LOGIN##</em>. Macro as such this will be replaced with value defined in dictionary (in this document this one is not replaced because we deliberately left it undefined in dictionary). If you change language, dictionary would change, and value of the macro presented in output document will be changed according to the language. </p>
<p>This method we described before as <em>&quot;by dictionary&quot;</em> differences. It  will do for most purposes and is especially suitable for menu options or other easily recognized elements on page. It is preffered method due to lower resource usage and speed. <a name="transliteration"></a></p>
<h2>Transliteration</h2><p>As we spoke before, other method do define differences is <em>&quot;by script&quot;</em>, which we call transliteration. Basically it means possibility to alter character from one language script with character from another. Our example is transliteration from cyrillic to latin script and vice versa. </p>
<p>However, transliteration is not limited to characters, it allows transliteration of strings too. This provides much more power to the library. You may transliterate whole words or expressions. It became another form of the dictionary but with significant difference: dictionary definitions work only on predefined language macros, transliteration works on free text.</p>
<p>Transilteration may be set in both language definition and dictionary. It is recomended to place transliteration definitions in language definition file if those definitions are needed all the time, for instance character conversions. </p>
<p>Here is an example of definition for serbian latin. It is child of serbian language and transliteration defines difference. Actualy it replaces cyrillic characters with latin ones. Due to number of characters this definition is long. Since this transliteration is a must for this language to work it is placed in language definition under property <strong>lng_def['parent_conversion_table']</strong> which we mentioned before. When transliteration like this is used there is no need for dictionaries. Serbian language is the same, no mater of script, so dictionaries loaded for parent serbian language will do all the job. This variant will just replace cyrilic with latin letters. </p>
<table width="650" border="0" align="center" cellpadding="0" cellspacing="0">
<tr>
<td>
<p>##LANGUAGE_DEFINITION##: ldef_sr-lat.php</p></td>
</tr>
</table>
<table width="650" border="1" align="center" cellpadding="0" cellspacing="0" bordercolor="#000000" bgcolor="#CCCCCC">
<tr>
<td>
<pre>&lt;?php<br>$lng_def['id'] = 'sr-lat';<br>$lng_def['name'] = 'srpski(lat)';<br>$lng_def['parent'] = 'sr';<br>$lng_def['codepage'] = 'utf-8';<br>$lng_def['parent_conversion_table'] = array (<br>	    &quot;А&quot; =&gt; &quot;A&quot;,<br>		&quot;Б&quot; =&gt; &quot;B&quot;,<br>		&quot;В&quot; =&gt; &quot;V&quot;,<br>		&quot;Г&quot; =&gt; &quot;G&quot;,<br>		&quot;Д&quot; =&gt; &quot;D&quot;,<br>		&quot;Ђ&quot; =&gt; &quot;Đ&quot;,<br>		&quot;Е&quot; =&gt; &quot;E&quot;,<br>		&quot;Ж&quot; =&gt; &quot;Ž&quot;,<br>		&quot;З&quot; =&gt; &quot;Z&quot;,<br>		&quot;И&quot; =&gt; &quot;I&quot;,<br>		&quot;Ј&quot; =&gt; &quot;J&quot;,<br>		&quot;К&quot; =&gt; &quot;K&quot;,<br>		&quot;Л&quot; =&gt; &quot;L&quot;,<br>		&quot;Љ&quot; =&gt; &quot;LJ&quot;,<br>		&quot;М&quot; =&gt; &quot;M&quot;,<br>		&quot;Н&quot; =&gt; &quot;N&quot;,<br>		&quot;Њ&quot; =&gt; &quot;NJ&quot;,<br>		&quot;О&quot; =&gt; &quot;O&quot;,<br>		&quot;П&quot; =&gt; &quot;P&quot;,<br>		&quot;Р&quot; =&gt; &quot;R&quot;,<br>		&quot;С&quot; =&gt; &quot;S&quot;,<br>		&quot;Ш&quot; =&gt; &quot;Š&quot;,<br>		&quot;Т&quot; =&gt; &quot;T&quot;,<br>		&quot;Ћ&quot; =&gt; &quot;Ć&quot;,<br>		&quot;У&quot; =&gt; &quot;U&quot;,<br>		&quot;Ф&quot; =&gt; &quot;F&quot;,<br>		&quot;Х&quot; =&gt; &quot;H&quot;,<br>		&quot;Ц&quot; =&gt; &quot;C&quot;,<br>		&quot;Ч&quot; =&gt; &quot;Č&quot;,<br>		&quot;Џ&quot; =&gt; &quot;DŽ&quot;,<br>		&quot;Ш&quot; =&gt; &quot;Š&quot;,<br>        &quot;а&quot; =&gt; &quot;a&quot;,<br>		&quot;б&quot; =&gt; &quot;b&quot;,<br>		&quot;в&quot; =&gt; &quot;v&quot;,<br>		&quot;г&quot; =&gt; &quot;g&quot;,<br>		&quot;д&quot; =&gt; &quot;d&quot;,<br>		&quot;ђ&quot; =&gt; &quot;đ&quot;,<br>		&quot;е&quot; =&gt; &quot;e&quot;,<br>		&quot;ж&quot; =&gt; &quot;ž&quot;,<br>		&quot;з&quot; =&gt; &quot;z&quot;,<br>		&quot;и&quot; =&gt; &quot;i&quot;,<br>		&quot;ј&quot; =&gt; &quot;j&quot;,<br>		&quot;к&quot; =&gt; &quot;k&quot;,<br>		&quot;л&quot; =&gt; &quot;l&quot;,<br>		&quot;љ&quot; =&gt; &quot;lj&quot;,<br>		&quot;м&quot; =&gt; &quot;m&quot;,<br>		&quot;н&quot; =&gt; &quot;n&quot;,<br>		&quot;њ&quot; =&gt; &quot;nj&quot;,<br>		&quot;о&quot; =&gt; &quot;o&quot;,<br>		&quot;п&quot; =&gt; &quot;p&quot;,<br>		&quot;р&quot; =&gt; &quot;r&quot;,<br>		&quot;с&quot; =&gt; &quot;s&quot;,<br>		&quot;ш&quot; =&gt; &quot;š&quot;,<br>		&quot;т&quot; =&gt; &quot;t&quot;,<br>		&quot;ћ&quot; =&gt; &quot;ć&quot;,<br>		&quot;у&quot; =&gt; &quot;u&quot;,<br>		&quot;ф&quot; =&gt; &quot;f&quot;,<br>		&quot;х&quot; =&gt; &quot;h&quot;,<br>		&quot;ц&quot; =&gt; &quot;c&quot;,<br>		&quot;ч&quot; =&gt; &quot;č&quot;,<br>		&quot;џ&quot; =&gt; &quot;x&quot;,<br>		&quot;ш&quot; =&gt; &quot;š&quot;,<br>		&quot;Ња&quot; =&gt; &quot;Nja&quot;,<br>		&quot;Ње&quot; =&gt; &quot;Nje&quot;,<br>		&quot;Њи&quot; =&gt; &quot;Nji&quot;,<br>		&quot;Њо&quot; =&gt; &quot;Njo&quot;,<br>		&quot;Њу&quot; =&gt; &quot;Nju&quot;,<br>		&quot;Ља&quot; =&gt; &quot;Lja&quot;,<br>		&quot;Ље&quot; =&gt; &quot;Lje&quot;,<br>		&quot;Љи&quot; =&gt; &quot;Lji&quot;,<br>		&quot;Љо&quot; =&gt; &quot;Ljo&quot;,<br>		&quot;Љу&quot; =&gt; &quot;Lju&quot;,<br>		&quot;Џа&quot; =&gt; &quot;Dža&quot;,<br>		&quot;Џе&quot; =&gt; &quot;Dže&quot;,<br>		&quot;Џи&quot; =&gt; &quot;Dži&quot;,<br>		&quot;Џо&quot; =&gt; &quot;Džo&quot;,<br>		&quot;Џу&quot; =&gt; &quot;Džu&quot;,<br>);<br>?&gt;<br>
</pre></td>
</tr>
</table>
<p>But, there may be some use for dictionaries. Rules of serbian language state that foreing names or expressions should be transliterated into cyrillic in a way they are pronounced. Therefore Microsoft becomes Мајкрософт, Linux becomes Линукс, and Windows becomes Виндоуз. When transliterating back to latin characters one may want to transliterate back to original foreign transcript. Thus we may use transliteration but now we can set it within dictionary file. Remeber, you may decide when to load dictionary files and manage resurce usage in that way. </p>
<table width="650" border="0" align="center" cellpadding="0" cellspacing="0">
<tr>
<td>
<p>##LANGUAGE_DICTIONARY##: ldct_sr-lat.php</p></td>
</tr>
</table>
<table width="650" border="1" align="center" cellpadding="0" cellspacing="0" bordercolor="#000000" bgcolor="#CCCCCC">
<tr>
<td>
<pre>&lt;?php<br>$lngt = array (<br>&quot;Мајкрософт&quot; =&gt; &quot;Microsoft&quot;,<br>&quot;Виндоуз&quot; =&gt; &quot;Windows&quot;,<br>&quot;имејл&quot; =&gt; &quot;e-mail&quot;,<br>&quot;Линукс&quot; =&gt; &quot;Linux&quot;);<br>?&gt;</pre></td>
</tr>
</table>
<p>Transliteration in dictionary file is set by defining <strong>$lngt</strong> array. Our example shows transliteration definition only but it will coexist with dictionary definition in the same file. </p>
<p>On the first glance, it seems that transliteration may replace dictionary, and that is true, but transliteration is, by its principles, slower method. It is recommended to use dictionaries whenever possible.<a name="languagefamilies" id="languagefamilies"></a></p>
<h2>Language families</h2>
<p>Several languages may have the same parent language. They are all, in fact,  variations of parent language. Languages that share the same parent including parent form language family. The family also has an ID and it is the same as ID of the parent language.</p>
<p>Language families are important. Due to definition it is clear that it may be necessary to fully define only parent language in a family. Variations contain only diffference rules, meaning that, when we prepare information that should be included in document, we do not have to prepare them in all variations of the language. It is enough to prepare information in parent language. Variation rules will alter that information if necessary.</p>
<p>This may be very handy when data is gathered from external documents or databases. Instead of having information prepared in advance for each language variation you may have it prepared only for parent language. Whole family of languages may use it and apply variation rules to create final output. </p>
<p>Note that in some occassions, families will not be of use - when gathered information closely depends on variations. How you wil deal with it is up to you. With careful planning you may avoid or reduce this situations.<a name="howtoprepare"></a></p><h2>How to prepare documents</h2><p>First you must decide what is source language for your site. Source language is treated as default one, one which will be showed to the visitor if he do not choose language. The best candidate is the language which you expect to be most used on your site. When source language is displayed the least or none processing is necessary which preserves resources. </p>
<p>When you decided which language is source you should create whole site using that language. You should of course take care about multilanguage features. Use language macros whenever possible. </p>
<p>Take care about images and other external documents. There are two important macros you may use for naming them.</p>
<p><strong>=&lt;id&gt;= </strong></p>
<p>This is  file language id macro. Instead of <em>&lt;id&gt;</em> place id of language. So, filenames shoud be in form <em>name=en=.jpg</em>, <em>name=en-us=.jpg</em>, <em>name=sr=.jpg</em>, <em>name=sr-lat=.jpg</em> etc. However, in design time, you shoud use bitmap which corresponds to source language. If your source language is english use <em>name=en=.jpg</em> while designing page. This will allow library to change image name and load one which is apropriate for display language. You may use this macro in names of any external documents that are loaded in page and even links to other documents. </p>
<p><strong>=%&lt;id&gt;= </strong></p>
<p>This is file language family id. It acts in similar way as <em>=&gt;id&gt;=,</em> except it treats family id's of source and display language. This is useful when you have to create static documents for languages or query database for information but regarding language. </p>
<p>As we said before, since language variations know how to alter text in parent language there is no need to prepare text for each language but only for parent languages. You have to use this macro to state that you want to load information that suits whole family not just display language. Filenames shoud be in form <em>name=%en=.jpg</em>, <em>name=%sr=.jpg</em> etc. If display language is <em>en</em> you will get <em>name=%en=.jpg</em>, if display language is <em>en-us </em>you will also get <em>name=%en=.jpg</em> because <em>en</em> is family language. Accordingly, if display languages are <em>sr</em> or <em>sr-lat</em>, or <em>sr-asc</em>, you will get <em>name=%sr=.jpg</em>.<a name="propertiesandmethods"></a></p><h2>Properties and methods </h2>
<p>Library offers range of functions to process languages. It also defines global variable called <em><strong>$lang_defs</strong></em> which is array containing definitions of all languages and loaded dictionaries and transliteration rules for source language and at least display language. Remember that if you need, you may fully load several languages and use them all on single page. You may read this variable but do not alter its concents. </p>
<p>Class properties</p>
<p><strong>$source_language</strong></p>
<p>This contains ID of language used in design mode for text, and naming documents. While designing site you use this language for contents. Take care of macros to alter contents for other languages, including ones for external documents. </p>
<p><strong>$display_language </strong></p>
<p> This is language that should be displayed for current user. Library will know how to handle  contents prepared in source language and display it in current language. You also may change display language within page to use several languages if needed.</p>
<p><strong> $lang_defs;</strong></p>
<p>Contains info about supported language definitions and dictionaires.  Definitions are stored as multidimensional array. The top array is indexed by language id,  and each record contains arrays with definitions for specific language. Language definition  is also multidimensional array</p>
<p> Structure:</p>
<p class="style1">$lang_defs;
<br>
&nbsp;&nbsp;[language id] =&gt; Array
  <br>
&nbsp;&nbsp;[id] =&gt; language id
  <br>
&nbsp;&nbsp;[name] =&gt; language name, used for description
  <br>
&nbsp;&nbsp;[codepage] =&gt; codepage that should be set for HTML document to present text using this language
  <br>
&nbsp;&nbsp;[is_source_lng] =&gt; 1, if this language is source language for site
  <br>
&nbsp;&nbsp;[parent] =&gt; languge id of parent language
  <br>
&nbsp;&nbsp;[dictionary] =&gt; Array
  <br>
&nbsp;&nbsp;&nbsp;&nbsp;[dictionary item] =&gt; value
  <br>
&nbsp;&nbsp;&nbsp;&nbsp;[dictionary item] =&gt; value
  <br>
&nbsp;&nbsp;&nbsp;&nbsp;[dictionary item] =&gt; value
  <br>
&nbsp;&nbsp;&nbsp;&nbsp;[dictionary item] =&gt; value
  <br>
&nbsp;&nbsp;[parent_conversion_table] =&gt; Array
  <br>
&nbsp;&nbsp;&nbsp;&nbsp;[source string] =&gt; replacement string
  <br>
&nbsp;&nbsp;&nbsp;&nbsp;[source string] =&gt; replacement string
  <br>
&nbsp;&nbsp;&nbsp;&nbsp;[source string] =&gt; replacement string
  <br>
&nbsp;&nbsp;&nbsp;&nbsp;[source string] =&gt; replacement string</p>
<p class="style1">&nbsp;&nbsp;[language id] =&gt; Array <br>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;. . . </p>
<p>This allows using multiple languages on the same page. It is not recomended to store complete dictionaires for multiple languages to reserve memory resources. Store only limited number of items which are needed to be  presented in several lanbguages on the same page like language names</p><p> <strong>function ULT($p_lang_dir)</strong><br>
Constructor function. Call this to create object. Optional parameter  is path to directory where language definition files are stored.  If not specified it defaults to lang/ directory. </p>
<p> <strong>function process($tpl_source)</strong><br>
Language processing:<br>
- replace all language macros with items according to dictionary<br>
 - replace all family id's in document (targeted to urls to external documents and links)<br>
 - replace all language id's in document (targeted to urls to external documents and links)<br>
- tanscribe characters and phrases from one language to another (or one language script to another)</p>
<p><strong>function set_display_language ($p_lang)</strong><br>
Set display language to $p_lang. If language id is invalid, it will set to source language.</p>
<p><strong>function set_default_language ($p_lang)</strong><br>
Set default language to $p_lang. If language id is invalid, it will set first language in array $lang_def.</p>
<p><strong>function set_language ($p_lang, $p_lang_dir)</strong><br>
Set language definition (add sub_array to $lang_defs) from language definition file. You may use this only if you want to load language definition manually.</p><p><strong>function load_language_defs($p_lang_dir = '')</strong><br>
Load definitions from all language definition files in target directory. If directory is not specified, current directory is used. </p>
<p> <strong> function language_defined ($p_lang)</strong><br>
Returns true if language definition is loaded.</p>
<p> <strong> function display_language_has_parent()</strong><br>
Returns true if display language has parent.</p>
<p> <strong>function transcribe ($p_text, $p_trans_table)</strong><br>
Do transription from one script to another using transcription table. This is for internal use. If you need some specific transcription, provide text and transcription table in form used in language definitions.</p>
<p> <strong>function transcribe_dictionary ($p_lang, $p_dictionary)</strong><br>
 Convert dictionary array from parent language to current. Used to transcribe from  different code page or script. If it is possible to create dictionary by  transcribing parent's dictionary then do this and do not define whole ditionary again. It will make dictionary maintenance easier. This is for internal use. </p>
<p> <strong>function transcribe_parent_language_dictionary ($p_lang)</strong><br>
Convert dictionary of loaded parent language to current. Used to transcribe from different code page or script.</p>
<p> <strong>function transcribe_document ($p_lang)</strong><br>
 If display language has parent language and source document is written in parent language then we should  transcribe document contents from parent language to display language. For internal use.</p>
<p> <strong> function filename_from_template ($p_dict_filename, $p_lang)</strong><br>
Creates full file name based on template and language. If language has parent then filename will be created due to parent language. Always use this to load files that corresponds to needed language.</p>
<p> <strong>function load_dictionary ($p_dict_filename, $p_lang, $p_add = false)</strong><br>
Load dictionary table from specified file into specified language definition.  If $p_add is true then definition is appended to already existing definitions.</p>
<p> <strong>function set_dictionary ($p_dict_filename, $p_lang, $p_add = false)</strong><br>
Load dictionary table from specified file into specified language definition.  If $p_add is true then definition is appended to already existing definitions. If language has parent, then parent's file will be loaded first and after that  child's file will beloaded. This helps dictionary maintenance. Most of the items may be stored in  parent's dictionary and only differences in childs dictionary (example, for 'en' as parent and  'en-us' as a child, most of the items are the same but some are not, like  'color'/'colour' pair. This allows you to have item 'colour' in parent dictionary of 'en' among  all others and just item 'color' for 'child 'en-us'.</p>
<p> <strong>function add_dictionary ($p_dict_filename, $p_lang)</strong><br>
 Load dictionary table from specified file into specified language definition.  It appends new definition to existing one.</p>
<p> <strong>function sync_child_dictionary ($p_lang)</strong><br>
 Synchronize child language dictionary with parent's. This will replace child dictionary with parent's (but transcribing it).</p>
<p> <strong>function is_family ($p_lang, $p_family)</strong><br>
 Check if language belongs to the family of languages (is parent or one of languages with the same parent)</p>
<p> <strong>function get_family ($p_lang)</strong><br>
Return family which language belongs to.</p>
<p><strong>function  block_start()</strong><br>
 Begin output buffering. All output after this will be buffered so language replacements may be made. </p>
<p> <strong>function block_end()</strong><br>
 End output buffering, do necessary language processing and display altered document.<a name="howtouse"></a></p>
<h2>How to use library</h2>
<p>Example abowe shows simple way to use this library. It will do the job if you have simple project and just need to add multilanguage support.</p>
<p>However, ULT is before all a library, not final solution. This just implements machanism to help you develop multilanguage support for your site. Therefore it does not contain high end methods. We suppose that you already have developed templating and parameter system and we do not want to interfere with it. You should be able to include this library in your project without need to alter way you are doing things.</p>
<p>You may store application parameters in some other way. Use it, instead of simple method presented in example. You may use sessions to store language information. Feel free to use it. You may have templating system. Use it. You may have database as bachkend for your site. Use it. You may even alter way of language and dictionary definition. Feel fre to do it if you have better way. </p><p>Take care of this: methods <strong>block_start()</strong> and <strong>block_end()</strong> are provided just to accomplish minimum functionality. You are supposed to have your own way to handle otput buffering, for purpose of templating for instance. If you do have output buffering implemented then do not use these two methods. You should use <strong>process()</strong> method do execute language processing instead. <a name="download"></a></p>
<h2>What's new</h2>
<p>02. feb. 2004 - First public version released. Version 0.3.9.</p>
<p>27. feb. 2004 - Documentation updated. Version 0.3.10.</p>
<p>30. march 2004 - Version 0.4.1 released. Global variable $lang_defs is removed and class property $lang_defs is introduced. </p><h2>Download</h2>
<p><a href="ult.zip">Download the latest version of ##Universal Language Tool for PHP##</a>.<a name="contact"></a></p>
<h2>Contact and support</h2>
<p>Universal Language Tool for PHP  is free software. You may use it and redistribute it. You  may change code to suit your needs but you may not distribute  changed code. You use this software on your own responsibility. We cannot be responsible for any result of this software use.</p>
<p>We do not provide email support. However, you may visit support <a href="http://www.datavoyage.net/oreska/viewforum.php?f=47" target="oreska">forum</a> or <a href="http://ult.datavoyage.com">home site</a>.</p>
<p>Author: Predrag Supurović, &copy;2004 Copyright by DataVoyage, <a href="http://www.datavoyage.com">http://www.datavoyage.com</a></p>
</td>
</tr>
<tr>
<td>&nbsp;</td>
</tr>
</table>
</body>
</html>
<?php

$dvl->block_end();

?>
Return current item: Universal Language Tool for PHP