CodeIgniter gettext with smarty or parser template without php code in view

Ngày 21 tháng 7 năm 2012 Trương Chương Dương
I've just finish a script to auto translate the text on CodeIgniter view with parser without any calling the gettext function in view. With this solution, you can apply the translated text via po file very easy and fastest.

The main feature of my library are:
  • Auto translated all text in view file into new languages
  • Support po file
  • Don't have to install smarty template, I'm using CodeIgniter parser, other powerful template parser, very easy to understanding and using.
  • NEW: Auto remove empty tag. E.g.: Some time, you have a tag or ..{/data} in the view, but in controller you don't init the variable data, so CI will render extractly the tag into final HTML. My library will remove it if you forgot assign every variable.
Eg.: The template are:


<h5>{t }Title is{/t}&  </h5>

<p>{t 1="<b>" 2="</b>"}Click here %1to see%2 me{/t}</p>

<p>{t 1="" 2="author"}The id is: %1 wrote by %2{/t}</p>

<p>{t 1="<a href=\"link here\">" 2="</a>"}Please lick on me%2{/t}</p>



So, all of the text above text will be translated to whatever language you want. Is it simple and powerful?

These are install step:

Step 1: Check your config.php file, my setting is: $config['subclass_prefix'] = 'My_', so if you change this value please also change all My_ prefix in my code when apply to your project.

Step 2: Open the file autoload.php, add My_language to the list of helper:
$autoload['helper'] = array('url', "My_language");

My_language helper will change the languages setting and load the po file, if you had other way to load the po file, please ignore this step.

Step 3: Also add My_parser library to the load list. Make sure that you load the library parser first and then My_parser. Don't switch the order or remove any of them.
$autoload['libraries'] = array('parser', 'My_parser');

This library will override the default CodeIgniter parser and add the translating feature.

Step 4: Create lang.po file in folder: application\language\<language_name>\LC_MESSAGES\lang.po
If you had setup to load the po file already, please ignore this step and the step 5 also.

Step 5: Create the file in application/helpers folder: my_language_helper.php and add the code below:

<?php&  if (!defined('BASEPATH')) exit('No direct script access allowed');
function set_translation_language($language){
    $lang_path = APPPATH.'language';
    setlocale(LC_ALL, $language.'.UTF-8');
    bindtextdomain('lang', $lang_path);

That helper will setup and load the po file, in any where in your controller/model or view, just call set_translation_language("lang_name"); to change the language.

Step 6: Create file application\libraries\My_Parser.php, and then enter the code below:
<?php  if  (!defined('BASEPATH'))
        exit('No  direct  script  access  allowed');
  *  My_Parser  Class
  *  @package          CodeIgniter
  *  @subpackage       Libraries
  *  @category         Parser
  *  @author           Truong  Chuong  Duong
  *  @copyright        Copyright  (c)  2012,  Truong  Chuong  Duong.  (
  *  @license  Open  Software  License  (OSL  3.0)
  *  @link   
  *  @since            Version  0.2 - Updated 2012-09-21
class  My_Parser  extends  CI_Parser

        function  __construct()

          *  Parse  a  template
          *  Parses  pseudo-variables  contained  in  the  specified  template,
          *  replacing  them  with  the  data  in  the  second  param
          *  @param        string
          *  @param        array
          *  @param        bool
          *  @return        string
        protected  function  _parse($template,  $data,  $return  =  false)
                if  ($template  ===  '')  {
                        return  false;

                //Create  new  array  for    and  {/key}  -  parse_pair
                $keys  =  array();
                preg_match_all("/({$this->l_delim}\/)([a-zA-Z0-9_]*)({$this->r_delim})/u",  $template,  $keys);
                $keys  =  $keys[2];
                foreach($keys  as  $key)
                        if  ($key  ==  "t")
                        if  (!isset($data[$key])  ||  !is_array($data[$key]))
                                $data[$key]  =  array();
                $final  =  parent::_parse($this->gettext($template),  $data,  $return);
                //Remove  all    -  parse_single
                $final  =  preg_replace("/({)([a-zA-Z0-9_]*)(})/u","",  $final);
                return  $final;

        //Fixed  the  text
        protected  function  fs($str)
                $str  =  stripslashes($str);
                $str  =  str_replace('"',  '\"',  $str);
                $str  =  str_replace("\n",  '\n',  $str);
                return  trim($str);

                Replace  the  params  in    tab.  
                        {t  1="value  1"  2="value  2"}This  is  param  1  value:  %1,  this  is  param  2  value:  %2,  param  2  again:  %2{/t}
                        This  is  param  1  value:  value  1,  this  is  param  2  value:  value  2,  param  2  again:  value  2
        protected  function  replaceParam($content,  $paramtext)
                $paramtext  =  str_replace('\\"',  """,  $paramtext);
                $tmp  =  explode('"',  $paramtext);

                for  ($i  =  0;  $i  <  count($tmp);  $i  +=  2)  {
                        if  (!isset($tmp[$i  +  1]))
                                $tmp[$i  +  1]  =  "";
                        $tmp[$i]  =  trim($tmp[$i],  "  =");
                        if  (empty($tmp[$i]))
                        $content  =  str_replace("%"  .  $tmp[$i],  $tmp[$i  +  1],  $content);
                return  $content;

        Replace  all    tab  to  the  translated  text
        protected  function  gettext($content)
                if  (empty($content))  {
                $ldq  =  $this->l_delim;
                $rdq  =  $this->r_delim;
                $cmd  =  preg_quote('t');
                $content  =  preg_replace("/($ldq)([a-zA-Z0-9_]*)($rdq)/u","_begin_val_$2_end_val_",  $content);
                $content  =  preg_replace("/(_begin_val_){$cmd}(_end_val_)/u","{{$cmd}}",  $content);
                preg_match_all("/{$ldq}\s*({$cmd})\s*([^{$rdq}]*){$rdq}([^{$ldq}]*){$ldq}\/\\1{$rdq}/",  $content,  $matches);
                for  ($i  =  0;  $i  <  count($matches[0]);  $i++)  {
                        $str  =  gettext($this->fs($matches[3][$i]));
                        if  (!empty($matches[2][$i]))  {
                                $str  =  $this->replaceParam($str,  $matches[2][$i]);
                        $content  =  str_replace($matches[0][$i],  $str,  $content);
                $content  =  str_replace(array("_begin_val_",  "_end_val_"),array($ldq,$rdq),  $content);
                return  $content;


//Auto  init  and  replace  the  default  parser
$CI  =&  get_instance();
$CI->parser  =  new  My_Parser();

/*  End  of  file  My_parser.php  */

From now, every thing is ready for you.
If you have any question, do not hesitate to contact me or write your comment on this post.
Đang tải dữ liệu...