xref: /netbsd-src/external/gpl2/gettext/dist/gettext-tools/doc/tutorial.html (revision 946379e7b37692fc43f68eb0d1c10daa0a7f3b6c)
1*946379e7Schristos<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML i18n//EN">
2*946379e7Schristos
3*946379e7Schristos<!--Converted with jLaTeX2HTML 2002-2-1 (1.70) JA patch-1.4
4*946379e7Schristospatched version by:  Kenshi Muto, Debian Project.
5*946379e7SchristosLaTeX2HTML 2002-2-1 (1.70),
6*946379e7Schristosoriginal version by:  Nikos Drakos, CBLU, University of Leeds
7*946379e7Schristos* revised and updated by:  Marcus Hennecke, Ross Moore, Herb Swan
8*946379e7Schristos* with significant contributions from:
9*946379e7Schristos  Jens Lippmann, Marek Rouchal, Martin Wilck and others -->
10*946379e7Schristos<HTML>
11*946379e7Schristos<HEAD>
12*946379e7Schristos<TITLE>A tutorial on Native Language Support using GNU gettext</TITLE>
13*946379e7Schristos<META NAME="description" CONTENT="A tutorial on Native Language Support using GNU gettext">
14*946379e7Schristos<META NAME="keywords" CONTENT="memo">
15*946379e7Schristos<META NAME="resource-type" CONTENT="document">
16*946379e7Schristos<META NAME="distribution" CONTENT="global">
17*946379e7Schristos
18*946379e7Schristos<META HTTP-EQUIV="Content-Type" CONTENT="text/html; charset=utf-8">
19*946379e7Schristos<META NAME="Generator" CONTENT="jLaTeX2HTML v2002-2-1 JA patch-1.4">
20*946379e7Schristos<META HTTP-EQUIV="Content-Style-Type" CONTENT="text/css">
21*946379e7Schristos
22*946379e7Schristos<!--
23*946379e7Schristos<LINK REL="STYLESHEET" HREF="memo.css">
24*946379e7Schristos-->
25*946379e7Schristos
26*946379e7Schristos</HEAD>
27*946379e7Schristos
28*946379e7Schristos<BODY >
29*946379e7Schristos
30*946379e7Schristos<!--Navigation Panel
31*946379e7Schristos<DIV CLASS="navigation">
32*946379e7Schristos<IMG WIDTH="81" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="next_inactive"
33*946379e7Schristos SRC="file:/usr/share/latex2html/icons/nx_grp_g.png">
34*946379e7Schristos<IMG WIDTH="26" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="up"
35*946379e7Schristos SRC="file:/usr/share/latex2html/icons/up_g.png">
36*946379e7Schristos<IMG WIDTH="63" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="previous"
37*946379e7Schristos SRC="file:/usr/share/latex2html/icons/prev_g.png">
38*946379e7Schristos<BR>
39*946379e7Schristos<BR><BR></DIV>
40*946379e7SchristosEnd of Navigation Panel-->
41*946379e7Schristos
42*946379e7Schristos<H1 ALIGN="CENTER">A tutorial on Native Language Support using GNU gettext</H1><DIV CLASS="author_info">
43*946379e7Schristos
44*946379e7Schristos<P ALIGN="CENTER"><STRONG>G.&nbsp;Mohanty</STRONG></P>
45*946379e7Schristos<P ALIGN="CENTER"><STRONG>Revision 0.3: 24 July 2004</STRONG></P>
46*946379e7Schristos</DIV>
47*946379e7Schristos
48*946379e7Schristos<H3>Abstract:</H3>
49*946379e7Schristos<DIV CLASS="ABSTRACT">
50*946379e7Schristos  The use of the GNU <TT>gettext</TT> utilities to implement support for native
51*946379e7Schristoslanguages is described here. Though, the language to be supported is
52*946379e7Schristosconsidered to be Oriya, the method is generally applicable. Likewise, while
53*946379e7SchristosLinux was used as the platform here, any system using GNU <TT>gettext</TT> should work
54*946379e7Schristosin a similar fashion.
55*946379e7Schristos
56*946379e7Schristos<P>
57*946379e7SchristosWe go through a step-by-step description of how to make on-screen messages
58*946379e7Schristosfrom a toy program to appear in Oriya instead of English; starting from the
59*946379e7Schristosprogramming and ending with the user's viewpoint. Some discussion is also made
60*946379e7Schristosof how to go about the task of translation.
61*946379e7Schristos</DIV>
62*946379e7Schristos<P>
63*946379e7Schristos<H1><A NAME="SECTION00010000000000000000">
64*946379e7SchristosIntroduction</A>
65*946379e7Schristos</H1>
66*946379e7SchristosCurrently, both commercial and free computer software is typically written and
67*946379e7Schristosdocumented in English. Till recently, little effort was expended towards
68*946379e7Schristosallowing them to interact with the user in languages other than English, thus
69*946379e7Schristosleaving the non-English speaking world at a disadvantage. However, that
70*946379e7Schristoschanged with the release of the GNU <TT>gettext</TT> utilities, and nowadays most GNU
71*946379e7Schristosprograms are written within a framework that allows easy translation of the
72*946379e7Schristosprogram message to languages other than English. Provided that translations
73*946379e7Schristosare available, the language used by the program to interact with the user can
74*946379e7Schristosbe set at the time of running it. <TT>gettext</TT> manages to achieve this seemingly
75*946379e7Schristosmiraculous task in a manner that simplifies the work of both the programmer
76*946379e7Schristosand the translator, and, more importantly, allows them to work independently
77*946379e7Schristosof each other.
78*946379e7Schristos
79*946379e7Schristos<P>
80*946379e7SchristosThis article describes how to support native languages under a system using
81*946379e7Schristosthe GNU <TT>gettext</TT> utilities. While it should be applicable to other versions of
82*946379e7Schristos<TT>gettext</TT>, the one actually used for the examples here is version
83*946379e7Schristos0.12.1. Another system, called <TT>catgets</TT>, described in the X/Open
84*946379e7SchristosPortability Guide, is also in use, but we shall not discuss that here.
85*946379e7Schristos
86*946379e7Schristos<P>
87*946379e7Schristos
88*946379e7Schristos<H1><A NAME="SECTION00020000000000000000">
89*946379e7SchristosA simple example</A>
90*946379e7Schristos</H1>
91*946379e7Schristos<A NAME="sec:simple"></A>Our first example of using <TT>gettext</TT> will be the good old Hello World program,
92*946379e7Schristoswhose sole function is to print the phrase ``Hello, world!'' to the terminal.
93*946379e7SchristosThe internationalized version of this program might be saved in hello.c as:
94*946379e7Schristos<PRE>
95*946379e7Schristos1    #include &lt;libintl.h&gt;
96*946379e7Schristos2    #include &lt;locale.h&gt;
97*946379e7Schristos3    #include &lt;stdio.h&gt;
98*946379e7Schristos4    #include &lt;stdlib.h&gt;
99*946379e7Schristos5    int main(void)
100*946379e7Schristos6    {
101*946379e7Schristos7      setlocale( LC_ALL, "" );
102*946379e7Schristos8      bindtextdomain( "hello", "/usr/share/locale" );
103*946379e7Schristos9      textdomain( "hello" );
104*946379e7Schristos10      printf( gettext( "Hello, world!\n" ) );
105*946379e7Schristos11      exit(0);
106*946379e7Schristos12    }
107*946379e7Schristos</PRE>
108*946379e7SchristosOf course, a real program would check the return values of the functions and
109*946379e7Schristostry to deal with any errors, but we have omitted that part of the code for
110*946379e7Schristosclarity. Compile as usual with <TT>gcc -o hello hello.c</TT>. The program should
111*946379e7Schristosbe linked to the GNU libintl library, but as this is part of the GNU C
112*946379e7Schristoslibrary, this is done automatically for you under Linux, and other systems
113*946379e7Schristosusing glibc.
114*946379e7Schristos
115*946379e7Schristos<H2><A NAME="SECTION00021000000000000000">
116*946379e7SchristosThe programmer's viewpoint</A>
117*946379e7Schristos</H2>
118*946379e7Schristos   As expected, when the <TT>hello</TT> executable is run under the default locale
119*946379e7Schristos(usually the C locale) it prints ``Hello, world!'' in the terminal. Besides
120*946379e7Schristossome initial setup work, the only additional burden faced by the programmer is
121*946379e7Schristosto replace any string to be printed with <TT>gettext(string)</TT>, i.e., to
122*946379e7Schristosinstead pass the string as an argument to the <TT>gettext</TT> function. For lazy
123*946379e7Schristospeople like myself, the amount of extra typing can be reduced even further by
124*946379e7Schristosa CPP macro, e.g., put this at the beginning of the source code file,
125*946379e7Schristos<PRE>
126*946379e7Schristos  #define _(STRING)    gettext(STRING)
127*946379e7Schristos</PRE>
128*946379e7Schristosand then use <TT>_(string)</TT> instead of <TT>gettext(string)</TT>.
129*946379e7Schristos
130*946379e7Schristos<P>
131*946379e7SchristosLet us dissect the program line-by-line.
132*946379e7Schristos
133*946379e7Schristos<OL>
134*946379e7Schristos<LI><TT>locale.h</TT> defines C data structures used to hold locale
135*946379e7Schristos  information, and is needed by the <TT>setlocale</TT> function. <TT>libintl.h</TT>
136*946379e7Schristos  prototypes the GNU text utilities functions, and is needed here by
137*946379e7Schristos  <TT>bindtextdomain</TT>, <TT>gettext</TT>, and <TT>textdomain</TT>.
138*946379e7Schristos</LI>
139*946379e7Schristos<LI>The call to <TT>setlocale</TT> () on line 7, with LC_ALL as the first argument
140*946379e7Schristos  and an empty string as the second one, initializes the entire current locale
141*946379e7Schristos  of the program as per environment variables set by the user. In other words,
142*946379e7Schristos  the program locale is initialized to match that of the user. For details see
143*946379e7Schristos  ``man <TT>setlocale</TT>.''
144*946379e7Schristos</LI>
145*946379e7Schristos<LI>The <TT>bindtextdomain</TT> function on line 8 sets the base directory for the
146*946379e7Schristos  message catalogs for a given message domain. A message domain is a set of
147*946379e7Schristos  translatable messages, with every software package typically having its own
148*946379e7Schristos  domain. Here, we have used ``hello'' as the name of the message domain for
149*946379e7Schristos  our toy program. As the second argument, /usr/share/locale, is the default
150*946379e7Schristos  system location for message catalogs, what we are saying here is that we are
151*946379e7Schristos  going to place the message catalog in the default system directory. Thus, we
152*946379e7Schristos  could have dispensed with the call to <TT>bindtextdomain</TT> here, and this
153*946379e7Schristos  function is useful only if the message catalogs are installed in a
154*946379e7Schristos  non-standard place, e.g., a packaged software distribution might have
155*946379e7Schristos  the catalogs under a po/ directory under its own main directory. See ``man
156*946379e7Schristos  <TT>bindtextdomain</TT>'' for details.
157*946379e7Schristos</LI>
158*946379e7Schristos<LI>The <TT>textdomain</TT> call on line 9 sets the message domain of the current
159*946379e7Schristos  program to ``hello,'' i.e., the name that we are using for our example
160*946379e7Schristos  program. ``man textdomain'' will give usage details for the function.
161*946379e7Schristos</LI>
162*946379e7Schristos<LI>Finally, on line 10, we have replaced what would normally have been,
163*946379e7Schristos<PRE>
164*946379e7Schristos  printf( "Hello, world!\n" );
165*946379e7Schristos</PRE>
166*946379e7Schristoswith,
167*946379e7Schristos<PRE>
168*946379e7Schristos  printf( gettext( "Hello, world!\n" ) );
169*946379e7Schristos</PRE>
170*946379e7Schristos(If you are unfamiliar with C, the <!-- MATH
171*946379e7Schristos $\backslash$
172*946379e7Schristos -->
173*946379e7Schristos<SPAN CLASS="MATH">&#92;</SPAN>n at the end of the string
174*946379e7Schristosproduces a newline at the end of the output.) This simple modification to all
175*946379e7Schristostranslatable strings allows the translator to work independently from the
176*946379e7Schristosprogrammer. <TT>gettextize</TT> eases the task of the programmer in adapting a
177*946379e7Schristospackage to use GNU <TT>gettext</TT> for the first time, or to upgrade to a newer
178*946379e7Schristosversion of <TT>gettext</TT>.
179*946379e7Schristos</LI>
180*946379e7Schristos</OL>
181*946379e7Schristos
182*946379e7Schristos<H2><A NAME="SECTION00022000000000000000">
183*946379e7SchristosExtracting translatable strings</A>
184*946379e7Schristos</H2>
185*946379e7Schristos  Now, it is time to extract the strings to be translated from the program
186*946379e7Schristossource code. This is achieved with <TT>xgettext</TT>, which can be invoked as follows:
187*946379e7Schristos<PRE><FONT color="red">
188*946379e7Schristos  xgettext -d hello -o hello.pot hello.c
189*946379e7Schristos</FONT></PRE>
190*946379e7SchristosThis processes the source code in hello.c, saving the output in hello.pot (the
191*946379e7Schristosargument to the -o option).
192*946379e7SchristosThe message domain for the program should be specified as the argument
193*946379e7Schristosto the -d option, and should match the domain specified in the call to
194*946379e7Schristos<TT>textdomain</TT> (on line 9 of the program source). Other details on how to use
195*946379e7Schristos<TT>gettext</TT> can be found from ``man gettext.''
196*946379e7Schristos
197*946379e7Schristos<P>
198*946379e7SchristosA .pot (portable object template) file is used as the basis for translating
199*946379e7Schristosprogram messages into any language. To start translation, one can simply copy
200*946379e7Schristoshello.pot to oriya.po (this preserves the template file for later translation
201*946379e7Schristosinto a different language). However, the preferred way to do this is by
202*946379e7Schristosuse of the <TT>msginit</TT> program, which takes care of correctly setting up some
203*946379e7Schristosdefault values,
204*946379e7Schristos<PRE><FONT color="red">
205*946379e7Schristos  msginit -l or_IN -o oriya.po -i hello.pot
206*946379e7Schristos</FONT></PRE>
207*946379e7SchristosHere, the -l option defines the locale (an Oriya locale should have been
208*946379e7Schristosinstalled on your system), and the -i and -o options define the input and
209*946379e7Schristosoutput files, respectively. If there is only a single .pot file in the
210*946379e7Schristosdirectory, it will be used as the input file, and the -i option can be
211*946379e7Schristosomitted.  For me, the oriya.po file produced by <TT>msginit</TT> would look like:
212*946379e7Schristos<PRE>
213*946379e7Schristos  # Oriya translations for PACKAGE package.
214*946379e7Schristos  # Copyright (C) 2004 THE PACKAGE'S COPYRIGHT HOLDER
215*946379e7Schristos  # This file is distributed under the same license as the PACKAGE package.
216*946379e7Schristos  # Gora Mohanty &lt;gora_mohanty@yahoo.co.in&gt;, 2004.
217*946379e7Schristos  #
218*946379e7Schristos  msgid ""
219*946379e7Schristos  msgstr ""
220*946379e7Schristos  "Project-Id-Version: PACKAGE VERSION\n"
221*946379e7Schristos  "Report-Msgid-Bugs-To: \n"
222*946379e7Schristos  "POT-Creation-Date: 2004-06-22 02:22+0530\n"
223*946379e7Schristos  "PO-Revision-Date: 2004-06-22 02:38+0530\n"
224*946379e7Schristos  "Last-Translator: Gora Mohanty &lt;gora_mohanty@yahoo.co.in&gt;\n"
225*946379e7Schristos  "Language-Team: Oriya\n"
226*946379e7Schristos  "MIME-Version: 1.0\n"
227*946379e7Schristos  "Content-Type: text/plain; charset=UTF-8\n"
228*946379e7Schristos  "Content-Transfer-Encoding: 8bit\n"
229*946379e7Schristos
230*946379e7Schristos  #: hello.c:10
231*946379e7Schristos  msgid "Hello, world!\n"
232*946379e7Schristos  msgstr ""
233*946379e7Schristos</PRE>
234*946379e7Schristos<TT>msginit</TT> prompted for my email address, and probably obtained my real name
235*946379e7Schristosfrom the system password file. It also filled in values such as the revision
236*946379e7Schristosdate, language, character set, presumably using information from the or_IN
237*946379e7Schristoslocale.
238*946379e7Schristos
239*946379e7Schristos<P>
240*946379e7SchristosIt is important to respect the format of the entries in the .po (portable
241*946379e7Schristosobject) file. Each entry has the following structure:
242*946379e7Schristos<PRE>
243*946379e7Schristos  WHITE-SPACE
244*946379e7Schristos  #  TRANSLATOR-COMMENTS
245*946379e7Schristos  #. AUTOMATIC-COMMENTS
246*946379e7Schristos  #: REFERENCE...
247*946379e7Schristos  #, FLAG...
248*946379e7Schristos  msgid UNTRANSLATED-STRING
249*946379e7Schristos  msgstr TRANSLATED-STRING
250*946379e7Schristos</PRE>
251*946379e7Schristoswhere, the initial white-space (spaces, tabs, newlines,...), and all
252*946379e7Schristoscomments might or might not exist for a particular entry. Comment lines start
253*946379e7Schristoswith a '#' as the first character, and there are two kinds: (i) manually
254*946379e7Schristosadded translator comments, that have some white-space immediately following the
255*946379e7Schristos'#,' and (ii) automatic comments added and maintained by the <TT>gettext</TT> tools,
256*946379e7Schristoswith a non-white-space character after the '#.' The <TT>msgid</TT> line contains
257*946379e7Schristosthe untranslated (English) string, if there is one for that PO file entry, and
258*946379e7Schristosthe <TT>msgstr</TT> line is where the translated string is to be entered. More on
259*946379e7Schristosthis later. For details on the format of PO files see gettext::Basics::PO
260*946379e7SchristosFiles:: in the Emacs info-browser (see Appdx.&nbsp;<A HREF="#sec:emacs-info">A</A> for an
261*946379e7Schristosintroduction to using the info-browser in Emacs).
262*946379e7Schristos
263*946379e7Schristos<H2><A NAME="SECTION00023000000000000000">
264*946379e7SchristosMaking translations</A>
265*946379e7Schristos</H2>
266*946379e7Schristos  The oriya.po file can then be edited to add the translated Oriya
267*946379e7Schristosstrings. While the editing can be carried out in any editor if one is careful
268*946379e7Schristosto follow the PO file format, there are several editors that ease the task of
269*946379e7Schristosediting PO files, among them being po-mode in Emacs, <TT>kbabel</TT>, gtranslator,
270*946379e7Schristospoedit, etc. Appdx.&nbsp;<A HREF="#sec:pofile-editors">B</A> describes features of some of
271*946379e7Schristosthese editors.
272*946379e7Schristos
273*946379e7Schristos<P>
274*946379e7SchristosThe first thing to do is fill in the comments at the beginning and the header
275*946379e7Schristosentry, parts of which have already been filled in by <TT>msginit</TT>. The lines in
276*946379e7Schristosthe header entry are pretty much self-explanatory, and details can be found in
277*946379e7Schristosthe gettext::Creating::Header Entry:: info node. After that, the remaining
278*946379e7Schristoswork consists of typing the Oriya text that is to serve as translations for
279*946379e7Schristosthe corresponding English string. For the <TT>msgstr</TT> line in each of the
280*946379e7Schristosremaining entries, add the translated Oriya text between the double quotes;
281*946379e7Schristosthe translation corresponding to the English phrase in the <TT>msgid</TT> string
282*946379e7Schristosfor the entry. For example, for the phrase ``Hello world!<!-- MATH
283*946379e7Schristos $\backslash$
284*946379e7Schristos -->
285*946379e7Schristos<SPAN CLASS="MATH">&#92;</SPAN>n'' in
286*946379e7Schristosoriya.po, we could enter ``&#x0b28;&#x0b2e;&#x0b38;&#x0b4d;&#x0b15;&#x0b3e;&#x0b30;<!-- MATH
287*946379e7Schristos $\backslash$
288*946379e7Schristos -->
289*946379e7Schristos<SPAN CLASS="MATH">&#92;</SPAN>n''. The final
290*946379e7Schristosoriya.po file might look like:
291*946379e7Schristos<PRE>
292*946379e7Schristos  # Oriya translations for hello example package.
293*946379e7Schristos  # Copyright (C) 2004 Gora Mohanty
294*946379e7Schristos  # This file is distributed under the same license as the hello example package.
295*946379e7Schristos  # Gora Mohanty &lt;gora_mohanty@yahoo.co.in&gt;, 2004.
296*946379e7Schristos  #
297*946379e7Schristos  msgid ""
298*946379e7Schristos  msgstr ""
299*946379e7Schristos  "Project-Id-Version: oriya\n"
300*946379e7Schristos  "Report-Msgid-Bugs-To: \n"
301*946379e7Schristos  "POT-Creation-Date: 2004-06-22 02:22+0530\n"
302*946379e7Schristos  "PO-Revision-Date: 2004-06-22 10:54+0530\n"
303*946379e7Schristos  "Last-Translator: Gora Mohanty &lt;gora_mohanty@yahoo.co.in&gt;\n"
304*946379e7Schristos  "Language-Team: Oriya\n"
305*946379e7Schristos  "MIME-Version: 1.0\n"
306*946379e7Schristos  "Content-Type: text/plain; charset=UTF-8\n"
307*946379e7Schristos  "Content-Transfer-Encoding: 8bit\n"
308*946379e7Schristos  "X-Generator: KBabel 1.3\n"
309*946379e7Schristos
310*946379e7Schristos  #: hello.c:10
311*946379e7Schristos  msgid "Hello, world!\n"
312*946379e7Schristos  msgstr "&#x0b28;&#x0b2e;&#x0b38;&#x0b4d;&#x0b15;&#x0b3e;&#x0b30;\n"
313*946379e7Schristos</PRE>
314*946379e7Schristos
315*946379e7Schristos<P>
316*946379e7SchristosFor editing PO files, I have found the <TT>kbabel</TT> editor suits me the best. The
317*946379e7Schristosonly problem is that while Oriya text can be entered directly into <TT>kbabel</TT>
318*946379e7Schristosusing the xkb Oriya keyboard layouts&nbsp;[<A
319*946379e7Schristos HREF="memo.html#xkb-oriya-layout">1</A>] and the entries
320*946379e7Schristosare saved properly, the text is not displayed correctly in the <TT>kbabel</TT> window
321*946379e7Schristosif it includes conjuncts. Emacs po-mode is a little restrictive, but strictly
322*946379e7Schristosenforces conformance with the PO file format. The main problem with it is that
323*946379e7Schristosit does not seem currently possible to edit Oriya text in Emacs. <TT>yudit</TT>
324*946379e7Schristosis the best at editing Oriya text, but does not ensure that the PO file format
325*946379e7Schristosis followed. You can play around a bit with these editors to find one that
326*946379e7Schristossuits your personal preferences. One possibility might be to first edit the
327*946379e7Schristosheader entry with <TT>kbabel</TT> or Emacs po-mode, and then use <TT>yudit</TT> to enter
328*946379e7Schristosthe Oriya text on the <TT>msgstr</TT> lines.
329*946379e7Schristos
330*946379e7Schristos<H2><A NAME="SECTION00024000000000000000">
331*946379e7SchristosMessage catalogs</A>
332*946379e7Schristos</H2>
333*946379e7Schristos  <A NAME="sec:catalog"></A>After completing the translations in the oriya.po file, it must be compiled to
334*946379e7Schristosa binary format that can be quickly loaded by the <TT>gettext</TT> tools. To do that,
335*946379e7Schristosuse:
336*946379e7Schristos<PRE><FONT color="red">
337*946379e7Schristos  msgfmt -c -v -o hello.mo oriya.po
338*946379e7Schristos</FONT></PRE>
339*946379e7SchristosThe -c option does detailed checking of the PO file format, -v makes the
340*946379e7Schristosprogram verbose, and the output filename is given by the argument to the -o
341*946379e7Schristosoption. Note that the base of the output filename should match the message
342*946379e7Schristosdomain given in the first arguments to <TT>bindtextdomain</TT> and <TT>textdomain</TT> on
343*946379e7Schristoslines 8 and 9 of the example program in Sec.&nbsp;<A HREF="#sec:simple">2</A>. The .mo
344*946379e7Schristos(machine object) file should be stored in the location whose base directory is
345*946379e7Schristosgiven by the second argument to <TT>bindtextdomain</TT>. The final location of the
346*946379e7Schristosfile will be in the sub-directory LL/LC_MESSAGES or LL_CC/LC_MESSAGES under
347*946379e7Schristosthe base directory, where LL stands for a language, and CC for a country. For
348*946379e7Schristosexample, as we have chosen the standard location, /usr/share/locale, for our
349*946379e7Schristosbase directory, and for us the language and country strings are ``or'' and
350*946379e7Schristos``IN,'' respectively, we will place hello.mo in /usr/share/locale/or_IN. Note
351*946379e7Schristosthat you will need super-user privilege to copy hello.mo to this system
352*946379e7Schristosdirectory. Thus,
353*946379e7Schristos<PRE><FONT color="red">
354*946379e7Schristos  mkdir -p /usr/share/locale/or_IN/LC_MESSAGES
355*946379e7Schristos  cp hello.mo /usr/share/locale/or_IN/LC_MESSAGES
356*946379e7Schristos</FONT></PRE>
357*946379e7Schristos
358*946379e7Schristos<H2><A NAME="SECTION00025000000000000000">
359*946379e7SchristosThe user's viewpoint</A>
360*946379e7Schristos</H2>
361*946379e7Schristos  Once the message catalogs have been properly installed, any user on the system
362*946379e7Schristoscan use the Oriya version of the Hello World program, provided an Oriya locale
363*946379e7Schristosis available. First, change your locale with,
364*946379e7Schristos<PRE><FONT color="red">
365*946379e7Schristos  echo $LANG
366*946379e7Schristos  export LANG=or_IN
367*946379e7Schristos</FONT></PRE>
368*946379e7SchristosThe first statement shows you the current setting of your locale (this is
369*946379e7Schristosusually en_US, and you will need it to reset the default locale at the end),
370*946379e7Schristoswhile the second one sets it to an Oriya locale.
371*946379e7Schristos
372*946379e7Schristos<P>
373*946379e7SchristosA Unicode-capable terminal emulator is needed to view Oriya output
374*946379e7Schristosdirectly. The new versions of both gnome-terminal and konsole (the KDE
375*946379e7Schristosterminal emulator) are Unicode-aware. I will focus on gnome-terminal as it
376*946379e7Schristosseems to have better support for internationalization. gnome-terminal needs to
377*946379e7Schristosbe told that the bytes arriving are UTF-8 encoded multibyte sequences. This
378*946379e7Schristoscan be done by (a) choosing Terminal <TT>-&gt;</TT> Character Coding <TT>-&gt;</TT>
379*946379e7SchristosUnicode (UTF-8), or (b) typing ``/bin/echo -n -e
380*946379e7Schristos'<!-- MATH
381*946379e7Schristos $\backslash$
382*946379e7Schristos -->
383*946379e7Schristos<SPAN CLASS="MATH">&#92;</SPAN>033%<!-- MATH
384*946379e7Schristos $\backslash$
385*946379e7Schristos -->
386*946379e7Schristos<SPAN CLASS="MATH">&#92;</SPAN>G''' in the terminal, or (c) by running
387*946379e7Schristos/bin/unicode_start. Likewise, you can revert to the default locale by (a)
388*946379e7Schristoschoosing Terminal <TT>-&gt;</TT> Character Coding <TT>-&gt;</TT> Current Locale
389*946379e7Schristos(ISO-8859-1), or (b) ``/bin/echo -n -e '<!-- MATH
390*946379e7Schristos $\backslash$
391*946379e7Schristos -->
392*946379e7Schristos<SPAN CLASS="MATH">&#92;</SPAN>033%<!-- MATH
393*946379e7Schristos $\backslash$
394*946379e7Schristos -->
395*946379e7Schristos<SPAN CLASS="MATH">&#92;</SPAN>@','' or
396*946379e7Schristos(c) by running /bin/unicode_stop. Now, running the example program (after
397*946379e7Schristoscompiling with gcc as described in Sec.&nbsp;<A HREF="#sec:simple">2</A>) with,
398*946379e7Schristos<PRE><FONT color="red">
399*946379e7Schristos  ./hello
400*946379e7Schristos</FONT></PRE>
401*946379e7Schristosshould give you output in Oriya. Please note that conjuncts will most likely
402*946379e7Schristosbe displayed with a ``halant'' as the terminal probably does not render Indian
403*946379e7Schristoslanguage fonts correctly. Also, as most terminal emulators assume fixed-width
404*946379e7Schristosfonts, the results are hardly likely to be aesthetically appealing.
405*946379e7Schristos
406*946379e7Schristos<P>
407*946379e7SchristosAn alternative is to save the program output in a file, and view it with
408*946379e7Schristos<TT>yudit</TT> which will render the glyphs correctly. Thus,
409*946379e7Schristos<PRE><FONT color="red">
410*946379e7Schristos  ./hello &gt; junk
411*946379e7Schristos  yudit junk
412*946379e7Schristos</FONT></PRE>
413*946379e7SchristosDo not forget to reset the locale before resuming usual work in the
414*946379e7Schristosterminal. Else, your English characters might look funny.
415*946379e7Schristos
416*946379e7Schristos<P>
417*946379e7SchristosWhile all this should give the average user some pleasure in being able to see
418*946379e7SchristosOriya output from a program without a whole lot of work, it should be kept in
419*946379e7Schristosmind that we are still far from our desired goal. Hopefully, one day the
420*946379e7Schristossituation will be such that rather than deriving special pleasure from it,
421*946379e7Schristosusers take it for granted that Oriya should be available and are upset
422*946379e7Schristosotherwise.
423*946379e7Schristos
424*946379e7Schristos<P>
425*946379e7Schristos
426*946379e7Schristos<H1><A NAME="SECTION00030000000000000000">
427*946379e7SchristosAdding complications: program upgrade</A>
428*946379e7Schristos</H1>
429*946379e7SchristosThe previous section presented a simple example of how Oriya language support
430*946379e7Schristoscould be added to a C program. Like all programs, we might now wish to further
431*946379e7Schristosenhance it. For example, we could include a greeting to the user by adding
432*946379e7Schristosanother <TT>printf</TT> statement after the first one. Our new hello.c source
433*946379e7Schristoscode might look like this:
434*946379e7Schristos<PRE>
435*946379e7Schristos1    #include &lt;libintl.h&gt;
436*946379e7Schristos2    #include &lt;locale.h&gt;
437*946379e7Schristos3    #include &lt;stdio.h&gt;
438*946379e7Schristos4    #include &lt;stdlib.h&gt;
439*946379e7Schristos5    int main(void)
440*946379e7Schristos6    {
441*946379e7Schristos7      setlocale( LC_ALL, "" );
442*946379e7Schristos8      bindtextdomain( "hello", "/usr/share/locale" );
443*946379e7Schristos9      textdomain( "hello" );
444*946379e7Schristos10      printf( gettext( "Hello, world!\n" ) );
445*946379e7Schristos11      printf( gettext( "How are you\n" ) );
446*946379e7Schristos12      exit(0);
447*946379e7Schristos13    }
448*946379e7Schristos</PRE>
449*946379e7SchristosFor such a small change, it would be simple enough to just repeat the above
450*946379e7Schristoscycle of extracting the relevant English text, translating it to Oriya, and
451*946379e7Schristospreparing a new message catalog. We can even simplify the work by cutting and
452*946379e7Schristospasting most of the old oriya.po file into the new one. However, real programs
453*946379e7Schristoswill have thousands of such strings, and we would like to be able to translate
454*946379e7Schristosonly the changed strings, and have the <TT>gettext</TT> utilities handle the drudgery
455*946379e7Schristosof combining the new translations with the old ones. This is indeed possible.
456*946379e7Schristos
457*946379e7Schristos<H2><A NAME="SECTION00031000000000000000">
458*946379e7SchristosMerging old and new translations</A>
459*946379e7Schristos</H2>
460*946379e7Schristos  As before, extract the translatable strings from hello.c to a new portable
461*946379e7Schristosobject template file, hello-new.pot, using <TT>xgettext</TT>,
462*946379e7Schristos<PRE><FONT color="red">
463*946379e7Schristos  xgettext -d hello -o hello-new.pot hello.c
464*946379e7Schristos</FONT></PRE>
465*946379e7SchristosNow, we use a new program, <TT>msgmerge</TT>, to merge the existing .po file with
466*946379e7Schristostranslations into the new template file, viz.,
467*946379e7Schristos<PRE><FONT color="red">
468*946379e7Schristos  msgmerge -U oriya.po hello-new.pot
469*946379e7Schristos</FONT></PRE>
470*946379e7SchristosThe -U option updates the existing
471*946379e7Schristos.po file, oriya.po. We could have chosen to instead create a new .po file by
472*946379e7Schristosusing ``-o <SPAN CLASS="MATH">&lt;</SPAN>filename<SPAN CLASS="MATH">&gt;</SPAN>'' instead of -U. The updated .po file will still
473*946379e7Schristoshave the old translations embedded in it, and new entries with untranslated
474*946379e7Schristos<TT>msgid</TT> lines. For us, the new lines in oriya.po will look like,
475*946379e7Schristos<PRE>
476*946379e7Schristos  #: hello.c:11
477*946379e7Schristos  msgid "How are you?\n"
478*946379e7Schristos  msgstr ""
479*946379e7Schristos</PRE>
480*946379e7SchristosFor the new translation, we could use, ``&#x0b06;&#x0b2a;&#x0b23;
481*946379e7Schristos&#x0b15;&#x0b3f;&#x0b2a;&#x0b30;&#x0b3f; &#x0b05;&#x0b1b;&#x0b28;&#x0b4d;&#x0b24;&#x0b3f;?'' in
482*946379e7Schristosplace of the English phrase ``How are you?'' The updated oriya.po file,
483*946379e7Schristosincluding the translation might look like:
484*946379e7Schristos<PRE>
485*946379e7Schristos  # Oriya translations for hello example package.
486*946379e7Schristos  # Copyright (C) 2004 Gora Mohanty
487*946379e7Schristos  # This file is distributed under the same license as the hello examplepackage.
488*946379e7Schristos  # Gora Mohanty &lt;gora_mohanty@yahoo.co.in&gt;, 2004.
489*946379e7Schristos  #
490*946379e7Schristos  msgid ""
491*946379e7Schristos  msgstr ""
492*946379e7Schristos  "Project-Id-Version: oriya\n"
493*946379e7Schristos  "Report-Msgid-Bugs-To: \n"
494*946379e7Schristos  "POT-Creation-Date: 2004-06-23 14:30+0530\n"
495*946379e7Schristos  "PO-Revision-Date: 2004-06-22 10:54+0530\n"
496*946379e7Schristos  "Last-Translator: Gora Mohanty &lt;gora_mohanty@yahoo.co.in&gt;\n"
497*946379e7Schristos  "Language-Team: Oriya\n"
498*946379e7Schristos  "MIME-Version: 1.0\n"
499*946379e7Schristos  "Content-Type: text/plain; charset=UTF-8\n"
500*946379e7Schristos  "Content-Transfer-Encoding: 8bit\n"
501*946379e7Schristos  "X-Generator: KBabel 1.3\n"
502*946379e7Schristos
503*946379e7Schristos  #: hello.c:10
504*946379e7Schristos  msgid "Hello, world!\n"
505*946379e7Schristos  msgstr "&#x0b28;&#x0b2e;&#x0b38;&#x0b4d;&#x0b15;&#x0b3e;&#x0b30;\n"
506*946379e7Schristos
507*946379e7Schristos  #: hello.c:11
508*946379e7Schristos  msgid "How are you?\n"
509*946379e7Schristos  msgstr "&#x0b06;&#x0b2a;&#x0b23; &#x0b15;&#x0b3f;&#x0b2a;&#x0b30;&#x0b3f; &#x0b05;&#x0b1b;&#x0b28;&#x0b4d;&#x0b24;&#x0b3f;?\n"
510*946379e7Schristos</PRE>
511*946379e7Schristos
512*946379e7Schristos<P>
513*946379e7SchristosCompile oriya.po to a machine object file, and install in the appropriate
514*946379e7Schristosplace as in Sec.&nbsp;<A HREF="#sec:catalog">2.4</A>. Thus,
515*946379e7Schristos<PRE><FONT color="red">
516*946379e7Schristos  msgfmt -c -v -o hello.mo oriya.po
517*946379e7Schristos  mkdir -p /usr/share/locale/or_IN/LC_MESSAGES
518*946379e7Schristos  cp hello.mo /usr/share/locale/or_IN/LC_MESSAGES
519*946379e7Schristos</FONT></PRE>
520*946379e7SchristosYou can test the Oriya output as above, after recompiling hello.c and running
521*946379e7Schristosit in an Oriya locale.
522*946379e7Schristos
523*946379e7Schristos<P>
524*946379e7Schristos
525*946379e7Schristos<H1><A NAME="SECTION00040000000000000000">
526*946379e7SchristosMore about <TT>gettext</TT> </A>
527*946379e7Schristos</H1>
528*946379e7SchristosThe GNU <TT>gettext</TT> info pages provide a well-organized and complete description
529*946379e7Schristosof the <TT>gettext</TT> utilities and their usage for enabling Native Language
530*946379e7SchristosSupport. One should, at the very least, read the introductory material at
531*946379e7Schristosgettext::Introduction::, and the suggested references in
532*946379e7Schristosgettext::Conclusion::References::. Besides the <TT>gettext</TT> utilities described in
533*946379e7Schristosthis document, various other programs to manipulate .po files are discussed in
534*946379e7Schristosgettext:Manipulating::. Finally, support for programming languages other than
535*946379e7SchristosC/C++ is discussed in gettext::Programming Languages::.
536*946379e7Schristos
537*946379e7Schristos<P>
538*946379e7Schristos
539*946379e7Schristos<H1><A NAME="SECTION00050000000000000000">
540*946379e7SchristosThe work of translation</A>
541*946379e7Schristos</H1>
542*946379e7Schristos  Besides the obvious program message strings that have been the sole focus of
543*946379e7Schristosour discussion here, there are many other things that require translation,
544*946379e7Schristosincluding GUI messages, command-line option strings, configuration files,
545*946379e7Schristosprogram documentation, etc. Besides these obvious aspects, there are a
546*946379e7Schristossignificant number of programs and/or scripts that are automatically generated
547*946379e7Schristosby other programs. These generated programs might also themselves require
548*946379e7Schristostranslation. So, in any effort to provide support for a given native language,
549*946379e7Schristoscarrying out the translation and keeping up with program updates becomes a
550*946379e7Schristosmajor part of the undertaking, requiring a continuing commitment from the
551*946379e7Schristoslanguage team. A plan has been outlined for the Oriya localization
552*946379e7Schristosproject&nbsp;[<A
553*946379e7Schristos HREF="memo.html#url:oriya-trans-plan">2</A>].
554*946379e7Schristos
555*946379e7Schristos<P>
556*946379e7Schristos
557*946379e7Schristos<H1><A NAME="SECTION00060000000000000000">
558*946379e7SchristosAcknowledgments</A>
559*946379e7Schristos</H1>
560*946379e7SchristosExtensive use has obviously been made of the GNU <TT>gettext</TT> manual in preparing
561*946379e7Schristosthis document. I have also been helped by an article in the Linux
562*946379e7SchristosJournal&nbsp;[<A
563*946379e7Schristos HREF="memo.html#url:lj-translation">3</A>].
564*946379e7Schristos
565*946379e7Schristos<P>
566*946379e7SchristosThis work is part of the project for enabling the use of Oriya under Linux. I
567*946379e7Schristosthank my uncle, N.&nbsp;M.&nbsp;Pattnaik, for conceiving of the project. We have all
568*946379e7Schristosbenefited from the discussions amidst the group of people working on this
569*946379e7Schristosproject. On the particular issue of translation, the help of H.&nbsp;R.&nbsp;Pansari,
570*946379e7SchristosA.&nbsp;Nayak, and M.&nbsp;Chand is much appreciated.
571*946379e7Schristos
572*946379e7Schristos<H1><A NAME="SECTION00070000000000000000">
573*946379e7SchristosThe Emacs info browser</A>
574*946379e7Schristos</H1>
575*946379e7Schristos<A NAME="sec:emacs-info"></A>You can start up Emacs from the command-line by typing ``emacs,'' or ``emacs
576*946379e7Schristos<SPAN CLASS="MATH">&lt;</SPAN>filename<SPAN CLASS="MATH">&gt;</SPAN>.'' It can be started from the menu in some desktops, e.g., on
577*946379e7Schristosmy GNOME desktop, it is under Main Menu <TT>-&gt;</TT> Programming <TT>-&gt;</TT>
578*946379e7SchristosEmacs. If you are unfamiliar with Emacs, a tutorial can be started by typing
579*946379e7Schristos``C-h t'' in an Emacs window, or from the Help item in the menubar at the
580*946379e7Schristostop. Emacs makes extensive use of the Control (sometimes labelled as ``CTRL''
581*946379e7Schristosor ``CTL'') and Meta (sometimes labelled as ``Edit'' or ``Alt'') keys. In
582*946379e7SchristosEmacs parlance, a hyphenated sequence, such as ``C-h'' means to press the
583*946379e7SchristosControl and `h' key simultaneously, while ``C-h t'' would mean to press the
584*946379e7SchristosControl and `h' key together, release them, and press the `t' key. Similarly,
585*946379e7Schristos``M-x'' is used to indicate that the Meta and `x' keys should be pressed at
586*946379e7Schristosthe same time.
587*946379e7Schristos
588*946379e7Schristos<P>
589*946379e7SchristosThe info browser can be started by typing ``C-h i'' in Emacs. The first time
590*946379e7Schristosyou do this, it will briefly list some commands available inside the info
591*946379e7Schristosbrowser, and present you with a menu of major topics. Each menu item, or
592*946379e7Schristoscross-reference is hyperlinked to the appropriate node, and you can visit that
593*946379e7Schristosnode either by moving the cursor to the item and pressing Enter, or by
594*946379e7Schristosclicking on it with the middle mouse button. To get to the <TT>gettext</TT> menu items,
595*946379e7Schristosyou can either scroll down to the line,
596*946379e7Schristos<PRE>
597*946379e7Schristos  * gettext: (gettext).                          GNU gettext utilities.
598*946379e7Schristos</PRE>
599*946379e7Schristosand visit that node. Or, as it is several pages down, you can locate it using
600*946379e7Schristos``I-search.'' Type ``C-s'' to enter ``I-search'' which will then prompt you
601*946379e7Schristosfor a string in the mini-buffer at the bottom of the window. This is an
602*946379e7Schristosincremental search, so that Emacs will keep moving you forward through the
603*946379e7Schristosbuffer as you are entering your search string. If you have reached the last
604*946379e7Schristosoccurrence of the search string in the current buffer, you will get a message
605*946379e7Schristossaying ``Failing I-search: ...'' on pressing ``C-s.'' At that point, press
606*946379e7Schristos``C-s'' again to resume the search at the beginning of the buffer. Likewise,
607*946379e7Schristos``C-r'' incrementally searches backwards from the present location.
608*946379e7Schristos
609*946379e7Schristos<P>
610*946379e7SchristosInfo nodes are listed in this document with a ``::'' separator, so
611*946379e7Schristosthat one can go to the gettext::Creating::Header Entry:: by visiting the
612*946379e7Schristos``gettext'' node from the main info menu, navigating to the ``Creating''
613*946379e7Schristosnode, and following that to the ``Header Entry'' node.
614*946379e7Schristos
615*946379e7Schristos<P>
616*946379e7SchristosA stand-alone info browser, independent of Emacs, is also available on many
617*946379e7Schristossystems. Thus, the <TT>gettext</TT> info page can also be accessed by typing
618*946379e7Schristos``info gettext'' in a terminal. <TT>xinfo</TT> is an X application serving as an
619*946379e7Schristosinfo browser, so that if it is installed, typing ``xinfo gettext'' from the
620*946379e7Schristoscommand line will open a new browser window with the <TT>gettext</TT> info page.
621*946379e7Schristos
622*946379e7Schristos<P>
623*946379e7Schristos
624*946379e7Schristos<H1><A NAME="SECTION00080000000000000000">
625*946379e7SchristosPO file editors</A>
626*946379e7Schristos</H1>
627*946379e7Schristos<A NAME="sec:pofile-editors"></A>While the <TT>yudit</TT> editor is adequate for our present purposes, and we are
628*946379e7Schristosplanning on using that as it is platform-independent, and currently the best
629*946379e7Schristosat rendering Oriya. This section describes some features of some editors that
630*946379e7Schristosare specialized for editing PO files under Linux. This is still work in
631*946379e7Schristosprogress, as I am in the process of trying out different editors before
632*946379e7Schristossettling on one. The ones considered here are: Emacs in po-mode, <TT>poedit</TT>,
633*946379e7Schristos<TT>kbabel</TT>, and <TT>gtranslator</TT>.
634*946379e7Schristos
635*946379e7Schristos<H2><A NAME="SECTION00081000000000000000">
636*946379e7SchristosEmacs PO mode</A>
637*946379e7Schristos</H2>
638*946379e7Schristos  Emacs should automatically enter po-mode when you load a .po file, as
639*946379e7Schristosindicated by ``PO'' in the modeline at the bottom. The window is made
640*946379e7Schristosread-only, so that you can edit the .po file only through special commands.  A
641*946379e7Schristosdescription of Emacs po-mode can be found under the gettext::Basics info node,
642*946379e7Schristosor type `h' or `?' in a po-mode window for a list of available commands. While
643*946379e7SchristosI find Emacs po-mode quite restrictive, this is probably due to unfamiliarity
644*946379e7Schristoswith it. Its main advantage is that it imposes rigid conformance to the PO
645*946379e7Schristosfile format, and checks the file format when closing the .po file
646*946379e7Schristosbuffer. Emacs po-mode is not useful for Oriya translation, as I know of no way
647*946379e7Schristosto directly enter Oriya text under Emacs.
648*946379e7Schristos
649*946379e7Schristos<H2><A NAME="SECTION00082000000000000000">
650*946379e7Schristospoedit</A>
651*946379e7Schristos</H2>
652*946379e7Schristos  XXX: in preparation.
653*946379e7Schristos
654*946379e7Schristos<H2><A NAME="SECTION00083000000000000000">
655*946379e7SchristosKDE: the kbabel editor</A>
656*946379e7Schristos</H2>
657*946379e7Schristos  <TT>kbabel</TT>&nbsp;[<A
658*946379e7Schristos HREF="memo.html#url:kbabel">4</A>] is a more user-friendly and configurable editor than
659*946379e7Schristoseither of Emacs po-mode or <TT>poedit</TT>. It is integrated into KDE, and offers
660*946379e7Schristosextensive contextual help. Besides support for various PO file features, it
661*946379e7Schristoshas a plugin framework for dictionaries, that allows consistency checks and
662*946379e7Schristostranslation suggestions.
663*946379e7Schristos
664*946379e7Schristos<H2><A NAME="SECTION00084000000000000000">
665*946379e7SchristosGNOME: the gtranslator editor</A>
666*946379e7Schristos</H2>
667*946379e7Schristos  XXX: in preparation.
668*946379e7Schristos
669*946379e7Schristos<H2><A NAME="SECTION00090000000000000000">
670*946379e7SchristosBibliography</A>
671*946379e7Schristos</H2><DL COMPACT><DD><P></P><DT><A NAME="xkb-oriya-layout">1</A>
672*946379e7Schristos<DD>
673*946379e7SchristosG.&nbsp;Mohanty,
674*946379e7Schristos<BR>A practical primer for using Oriya under Linux, v0.3,
675*946379e7Schristos<BR><TT><A NAME="tex2html1"
676*946379e7Schristos  HREF="http://oriya.sarovar.org/docs/getting_started/index.html">http://oriya.sarovar.org/docs/getting_started/index.html</A></TT>, 2004,
677*946379e7Schristos<BR>Sec.&nbsp;6.2 describes the xkb layouts for Oriya.
678*946379e7Schristos
679*946379e7Schristos<P></P><DT><A NAME="url:oriya-trans-plan">2</A>
680*946379e7Schristos<DD>
681*946379e7SchristosG.&nbsp;Mohanty,
682*946379e7Schristos<BR>A plan for Oriya localization, v0.1,
683*946379e7Schristos<BR><TT><A NAME="tex2html2"
684*946379e7Schristos  HREF="http://oriya.sarovar.org/docs/translation_plan/index.html">http://oriya.sarovar.org/docs/translation_plan/index.html</A></TT>,
685*946379e7Schristos  2004.
686*946379e7Schristos
687*946379e7Schristos<P></P><DT><A NAME="url:lj-translation">3</A>
688*946379e7Schristos<DD>
689*946379e7SchristosLinux Journal article on internationalization,
690*946379e7Schristos<BR><TT><A NAME="tex2html3"
691*946379e7Schristos  HREF="http://www.linuxjournal.com/article.php?sid=3023">http://www.linuxjournal.com/article.php?sid=3023</A></TT>.
692*946379e7Schristos
693*946379e7Schristos<P></P><DT><A NAME="url:kbabel">4</A>
694*946379e7Schristos<DD>
695*946379e7SchristosFeatures of the kbabel editor,
696*946379e7Schristos<BR><TT><A NAME="tex2html4"
697*946379e7Schristos  HREF="http://i18n.kde.org/tools/kbabel/features.html">http://i18n.kde.org/tools/kbabel/features.html</A></TT>.
698*946379e7Schristos</DL>
699*946379e7Schristos
700*946379e7Schristos<H1><A NAME="SECTION000100000000000000000">
701*946379e7SchristosAbout this document ...</A>
702*946379e7Schristos</H1>
703*946379e7Schristos <STRONG>A tutorial on Native Language Support using GNU gettext</STRONG><P>
704*946379e7SchristosThis document was generated using the
705*946379e7Schristos<A HREF="http://www.latex2html.org/"><STRONG>LaTeX</STRONG>2<tt>HTML</tt></A> translator Version 2002-2-1 (1.70)
706*946379e7Schristos<P>
707*946379e7SchristosCopyright &#169; 1993, 1994, 1995, 1996,
708*946379e7Schristos<A HREF="http://cbl.leeds.ac.uk/nikos/personal.html">Nikos Drakos</A>,
709*946379e7SchristosComputer Based Learning Unit, University of Leeds.
710*946379e7Schristos<BR>Copyright &#169; 1997, 1998, 1999,
711*946379e7Schristos<A HREF="http://www.maths.mq.edu.au/~ross/">Ross Moore</A>,
712*946379e7SchristosMathematics Department, Macquarie University, Sydney.
713*946379e7Schristos<P>
714*946379e7SchristosThe command line arguments were: <BR>
715*946379e7Schristos <STRONG>latex2html</STRONG> <TT>-no_math -html_version 4.0,math,unicode,i18n,tables -split 0 memo</TT>
716*946379e7Schristos<P>
717*946379e7SchristosThe translation was initiated by Gora Mohanty on 2004-07-24
718*946379e7Schristos<DIV CLASS="navigation"><HR>
719*946379e7Schristos
720*946379e7Schristos<!--Navigation Panel
721*946379e7Schristos<IMG WIDTH="81" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="next_inactive"
722*946379e7Schristos SRC="file:/usr/share/latex2html/icons/nx_grp_g.png">
723*946379e7Schristos<IMG WIDTH="26" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="up"
724*946379e7Schristos SRC="file:/usr/share/latex2html/icons/up_g.png">
725*946379e7Schristos<IMG WIDTH="63" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="previous"
726*946379e7Schristos SRC="file:/usr/share/latex2html/icons/prev_g.png">
727*946379e7Schristos<BR></DIV>
728*946379e7SchristosEnd of Navigation Panel-->
729*946379e7Schristos
730*946379e7Schristos<ADDRESS>
731*946379e7SchristosGora Mohanty
732*946379e7Schristos2004-07-24
733*946379e7Schristos</ADDRESS>
734*946379e7Schristos</BODY>
735*946379e7Schristos</HTML>
736