Translations

[Home]   [Puzzles & Projects]    [Delphi Techniques]   [Math Topics]   [Library]   [Utilities]

 

Search

 

Search DelphiForFun.org only

Support DFF

 If you shop at Amazon anyway,  consider using this link. We receive a few cents from each purchase.   Thanks.

In Association with Amazon.com

 

Support DFF

 If you benefit from the website,  in terms of knowledge, entertainment value, or something otherwise useful, consider making a donation via PayPal  to help defray the costs.  (No PayPal account necessary to donate via credit card.)  Transaction is secure.

 

 

Contact

Feedback:  Send an e-mail with your comments about this program (or anything else).

 

Search DelphiForFun.org only

 

 

 

 

Problem Description

A "Hello World" program to examine techniques and pitfalls in "Internationaliziing" a program to support foreign languages.  

Background & Techniques

A while ago I had the chance to convert a program to support an Italian non-profit organization intending to use my Reaction Times program with non English-speaking  young people.  There are some good, free, tools but it took a few days of study to pick up on how to use them for even the simplest case with a single language.  l decided to write a "do-nothing" program so I could concentrate on how to generalize it to handle multiple languages.

The free tools I used are dxGetText, a translation toolkit for Delphi   and  PoEdit, which helps enter translations for strings extracted from your program by dxGetText.  Both programs are also available from SourceForge.net.

I'll outline the program first and then provide some notes about the use of the above tools used to implement it.  The program displays one of two messages: "Hello World!" or "Goodbye!"  toggled by a "Change message" button.  A radio group allows choice of several languages (currently English, French, German, Spanish, and "Southern USA" just for fun).   The messages and all of the displayed text (titles, labels, and radio group contents) are displayed in the chosen language.  The language choices  in the radio group are built dynamically, so additional languages could be added simply by adding translation sets (.po and .mo files) for other languages in the defined location ("locale/xx/Lc_messages" folder within the folder containing the source code and recompiling the program.  "xx" in the previous folder structure is the two letter id code for the language ( "fr", "de", and "es" for the initial set).  These language id's and the languages names are defined in  ISO Standard 639.1.  

I have not tested the program with a "locale" language other than English.  In fact, I'm not even sure how to do that.  It should recognize and honor the other three languages but  I'm sure someone  will let me know the symptoms when it doesn't work!   

Here are some notes about elements of multi-language support as implemented here:

  1.  Uses Dxgettext GNU freeware to translate and PoEdit freeware to define string translations in default.po files (one file per language, each in its own folder)
  2. Add gnuGetText unit to Uses clauses.
  3. Add gettext('xxx') to translate all 'xxx' constant strings. Use _('xxx') as a shortcut alias  for gettext.
  4. Install DXGettext to add the "template" building option to the  folder context menu. It will scan .pas, .dfm, .dpr, .res files in that folder to build "default.po" file of most strings found within those files.
  5. Define folders for translations within the project folder: default folder names "project/locale/xx/LC_Messages/" where 'xx' is the two letter language id.
  6. Copy default.po from Step 4 to each specific language folder defined in Step 5.  (After the initial run, use the "merge" option, see Step 9.)
  7. Run poEdit on the Step 6 file to manually translate strings. Double click .po file to start poEdit. To avoid error message, under "catalog/settings/projects" tab, define a project/version name. Select a string in upper window, enter translation in window at the bottom of the form. Make sure "Windows" line separator option is checked under "File/ Preferences/Editor" and you will be able fine tune editing with Notepad.
  8. Closing PoEdit will create .mo file used at run-time.
  9. To avoid reentering translations after program changes are made, a new .po file can be merged with old by right click old .po file and selecting "Merge" option.
  10. poEdit doesn't allow deletions of strings as far as I could tell, so I used Notepad for that kind of cleanup.  Strings which no longer appear in the source code files are converted to comments in the .po file when a new template is merged, but  text in forms remain.  If it is always overwritten by the program entris for the forms text tmay be deleted using Notepad.  Right click .po file and select "Create .mo file" after editing with Notepad. (poEdit will automatically rebuild .mo file when closing). If rebuilding  .mo returns an error, rerun poEdit for detail error and fix-up.
  11. Finally, when ready to distribute the  program, right click "Embed translations"  on the context menu for the executable in order to embed the .mo translation files into that file.

One more note, the dxGettext manual has sample code which retrieves the two letter codes for the target languages  included with a program, but I could not find a clean way to convert the two letter ISO639.1 codes to language names, so i made one.  File ISO639V1.txt included in the downloads has the 200 or so codes and names defined by the standard.  I load that file into a string list, LanguageTable, and use it to display the names of the languages found.          

Running/Exploring the Program 

bulletDownload source
bulletDownload  executable

Suggestions for Further Explorations

I'm sure that the ISO638V1.txt file could be incorporated as a resource into the executable, but I on't have time to work on it right now.  Sounds like a candidate for another demo program!

 

Original:  July 17, 2011

Modified:  July 18, 2011

  [Feedback]   [Newsletters (subscribe/view)] [About me]
Copyright 2000-2014, Gary Darby    All rights reserved.