Interface Language | Translations | Localization | Internationalization | edit navbar

Here you can find information about contributing to the localization (l10n) of Freeciv. The intended audience is translators, rather than coders or players.

Freeciv uses the gettext system for internationalization and localization support. See the gettext documentation for further information.

For a quick overview of gettext, see Freeciv's Gettext Guide and gettext notes.

How to Contribute[]

If a locale is already supported, try contacting the existing maintainer(s). See the Translations page for a list of existing locales, their status, and some contact details; also look in the existing po-file(s), which may have more up-to-date contact details. (However, if a translation looks abandoned, it may be appropriate for you to take it over.)

If you want to contribute a new locale, you should let us know your intentions, preferably by posting to the freeciv-i18n mailing list.

You may also want to apply for source tree access to be able to add and maintain your translation, but it's not mandatory -- we can commit translations for you.

You may also find information of general interest to all contributors here, including how to submit changes.

See the info file about gettext for definitive information on its use.

How to add support for new languages[]

Suppose you want to add support for Cornish (the kw locale). One way to do this is as follows:

  1. Decide which branch you are going to start translating.
  2. Download and install the Freeciv source from Git.
  3. List the new translation for the build system
    1. Freeciv-3.1 and later: Modify the LINGUAS file for all the translation domains translations/*/LINGUAS to include 'kw' line. At the moment we don't support adding translation just for some domain(s).
    2. Freeciv-3.0 and earlier: Modify the line containig ALL_LINGUAS to include 'kw':
      ALL_LINGUAS="es fr"
      ALL_LINGUAS="es fr kw"
  4. Regenerate the autoconf stuff:
    $ ./
  5. Configure Freeciv:
    $ ./configure
  6. Change to the translations/core directory:
    $ cd ./translations/core
  7. Create the freeciv-core.pot file:
    $ make freeciv-core.pot
  8. Copy freeciv-core.pot to kw.pox (the auxiliary .po file):
    $ cp freeciv-core.pot kw.pox
  9. Edit the kw.pox file and translate all entries.
  10. Rename kw.pox to kw.po:
    $ mv kw.pox kw.po
  11. Make the file:
    $ make

(However, this is not the only way. You can get a reasonably recent freeciv.pot for your branch from , then skip to step 8.)

If poedit returns errors[]

If poedit returns errors when you try to save your new po file, please remove the following lines from the very top of the file:

#, fuzzy
msgid ""
msgstr ""

How to update your translations[]

As the code continues to change, new strings may be added and old strings may be changed or removed.

Suppose you now want to update the Polish translation you made by following the above steps. You have to do the following things:

  1. Download and install the Freeciv source.
    (This should now include your previous kw.po file.)
    Alternatively, for quick access to po translation files, you can grab semi-regularly generated files at or nightly generated source tarball containing, among other sources, up-to-date po files: .
  2. Configure Freeciv:
    $ ./configure
  3. For each of the translation directories you're working on (just po in 2.4 and prior; translations/freeciv, translations/nations etc on 2.5 and later):
    1. Change to the translation directory:
      $ cd ./translations/freeciv
    2. Create the auxiliary .po file:
      $ make kw.pox
      (This will contain a merge of your previous translations and changes in the source code.)
    3. Edit the kw.pox file and update all entries.
    4. Rename kw.pox to kw.po:
      $ mv kw.pox kw.po
    5. Make the file:
      $ make

On new branches you can use 'make update-po' on the translation directory. This will update the .pot file and then update all the .po files. Remember to 'make install' on the root of the source directory to install the compiled .gmo files to check you translation at runtime.

How to choose the branch to work on[]

There are many stable branches in Freeciv's Git repository. Here are some tips on how to choose the right one to work on:

  • Look at the latest stable public version of Freeciv - currently 3.1.2 - chances are that more bugfix releases will be made from this branch, and strings should be relatively stable.
  • Check on the download page whether there are any recent beta releases available. If there are, chances are even better that several releases will be made from this branch over the coming months. If you are starting a new translation and expect to take a while to complete it, you may want to start with a beta or development branch rather than a stable branch that might be retired before you complete; but strings will be more volatile.

It's best to avoid working directly on master -- as this is where major new features are developed, strings are unstable, and you may find that you translate strings that never make it into a release.

Work done on an older branch can always be migrated to newer branches, so nothing is lost by picking an older branch.

If in doubt, ask on freeciv-i18n for current advice.

How to choose which strings to work on[]

From Freeciv 2.5 onwards, the translatable strings are split into several sets, and translators can choose how much to localize:

freeciv / core
The core strings used by the game engine, the supplied rulesets and scenarios, and a relatively small set of 'core' nations in the supplied rulesets. Every localization should include this set. (Renamed to 'core' from S3_0 onwards.)
The extended nation set. This contains hundreds of additional nation descriptions, which adds up to a lot of translatable text, which not all contributors are willing to commit to maintaining. These nations are no longer presented to players by default, although it is easy to reach them; players get a warning that the nations may not be localized.
(In 2.4 and earlier versions, these were included in the main set of strings, although many localizations didn't fully translate them.)
(from 2.6) A small catalogue of strings related to the ruleset editor.

These are maintained as separate string catalogues under the translations directory, each with their own freeciv*.pot and language .po file. A small number of strings appear in multiple files. (We don't currently have good support for translators who want to work on all these strings in a single catalogue, nor for reconciling conflicts/duplicates between string catalogues.)

2.4 and prior had a single string catalogue (po). Migrating a localization to the split world is slightly involved, and is best left to the developers; ask on freeciv-i18n. (For the brave, a script to help with this is attached to GNAPATCH#4650.) All dormant translations have already been migrated.

How to keep two branches in sync[]

Freeciv develops using Git branches. Whenever we prepare for a release, we branch off development at that point, and keep a copy of the code that we try to do only bugfixes on, and which will eventually become the next stable release. If you do not know how to keep translations in sync between this stable branch and the rapidly moving development branch, you could be in for a nightmare.

However, apart from the special case of moving from S2_4 to S2_5 or later, keeping things in sync is not so difficult. Decide on one branch (stable or development) that you will focus on. Make your changes there, then merge your changes from that branch over into the other with the 'msgmerge' program.

Given you have completed the translation for the stable branch, and want to feed your translations into the development branch. cd into translations/core and call it like this:

make freeciv-core.pot
msgmerge --compendium=de.po PATH-TO-STABLE-DE.PO freeciv-core.pot -o de.pox

for example

make freeciv-core.pot
msgmerge --compendium=de.po ../../stable/translations/core/de.po freeciv-core.pot -o de.pox

This is identical to calling 'make de.pox', except that you also merge in a third .po file as well.

How to create the most current freeciv*.pot file[]

To create the most current freeciv*.pot file yourself (instead of using our generated files), you would have to do the following things:

  1. Check-out the latest Freeciv source from the Git repository.
    See here for information on using Git.
  2. Configure Freeciv:
    $ ./configure
  3. Change to the directories of the translations you're maintaining (./po on 2.4, translations/freeciv or translations/core or translations/nations or ... on later branches):
    $ cd ./translations/core
  4. Create the freeciv-core.pot file:
    $ make freeciv-core.pot

Other translation domains' .pot files are named differently, e.g., freeciv-nations.pot.

How to handle qualified translatable strings[]

Some strings are too ambiguous to be easily translated. The canonical example is the English word "game", which is used in Freeciv in two roles:

  1. The game we play: Freeciv; the name of the first menu item.
  2. The terrain special of game animals -- animals hunted for food.

These are two very different concepts, and must frequently be translated into different words. However, they often occur in the code as the sole content of a string. If they were internationalized in the normal manner, they would be combined into a single entry in the freeciv.pot file:

#: menu.c:123 terrain.c:321 
msgid "Game" 
msgstr "" 

And, hence, could not be translated into the two distinct words it needs be.

Freeciv solves this problem by introducing the concept of qualified translatable strings. Strings are "qualified" by prefixing them with a descriptive tag, surrounded by "?" and ":".

Using our game example, the qualified strings might be:


And these would show up as two distinct entries in the freeciv.pot file:

#: menu.c:123 
msgid "?play:Game" 
msgstr "" 
#: terrain.c:321 
msgid "?animals:Game" 
msgstr "" 

These could now be translated as needed. For example, in de.po:

#: menu.c:123 
msgid "?play:Game" 
msgstr "?Spiel:Spiel" 
#: terrain.c:321 
msgid "?animals:Game" 
msgstr "?Tiere:Wild" 

Which would appear to the user as:

Spiel and Wild

Note that you don't have to translate the descriptive tags, as they are never shown to the user. For example:

#: menu.c:123 
msgid "?play:Game" 
msgstr "Spiel" 
#: terrain.c:321 
msgid "?animals:Game" 
msgstr "Wild"

How to change the order of arguments[]

It is sometimes necessary to rearrange the arguments in a string, especially in languages with reverse word order from English.

If you have string consisting of two arguments "%s %s" you can do "%2$s %1$s" to reverse their order. To the % part of an argument formattor, you add X$ where X is the the order you want the argument in.

Note that if the arguments are mixed (for example %s and %d, every item must be numbered). For example, to change the order of arguments in "%s and %d other unit lost to an attack from the %s %s", these are treated as if they were "%1$s and %2$d other unit lost to an attack from the %3$s %4$s.". So in Gaelic for example, this would become "Chaidh %1$s agus %2$d aonad eile a chall an cois ionnsaigh %4$s %3$s."

If the string already contains a number, for example "%2d: The %s ruler %s scored %d points" then treat any such number-letter combination as if it was one unit, i.e. in Gaelic, this becomes "%1$2d: Fhuair %3$s, riaghlaiche %2$s %4$d phuing".

How to check your translations for common errors[]

Before submitting your translations for inclusion in Git, you should check to make sure they don't contain obvious errors.

First, near the top of your .po file you should have an entry that looks something like:

msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"POT-Creation-Date: 2000-04-07 13:50-0400\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=CHARSET\n"
"Content-Transfer-Encoding: ENCODING\n"

(perhaps with some of the fields filled in). This entry must exist, and must contain at least:

msgid ""
msgstr ""
"POT-Creation-Date: 2000-04-07 13:50-0400\n"

Second, you should do a quick check that gettext provides to validate your .po file:

% cd po
% msgfmt -v -c --stat de.po

If any errors exist in the specified .po file, a description of each problem will be printed.

How to check in your translations[]

(This is not mandatory; you can post to the freeciv-i18n list and ask someone to do this for you.)

You need a Git checkout and write access to the tree for this.

From the source root directory, do:

% git commit --message "what I did with the po file, updates etc." translations/core/de.po

Localization Mini-FAQ[]

These address a few problems and questions about Localization.

How does Freeciv determine what language it should use?[]

See also Interface Language.

Freeciv checks the environment variable $LANG for that, so you should set it; for example, to use German, issue the bash command "export LANG=de_DE" before you start civserver or civclient, or "setenv LANG de_DE" if you use tcsh. If you still get English, perhaps you are trying an invalid value (the value "de" instead of "de_DE" will probably fail to work) or the Freeciv software was compiled without localization support.

When I try to "make freeciv.pot", no file is generated.[]

It's likely that ./configure didn't find the GNU version of xgettext. Look at the output from ./configure, and if you find something like:

checking for xgettext... :

(note, just a ":", not a path to xgettext) then ./configure could not find any version of xgettext. Or, if you see something like:

checking for xgettext... /usr/bin/xgettext
found xgettext program is not GNU xgettext; ignore it

then ./configure could not find the GNU version of xgettext.

In either case, you will need to get and install the GNU version of the gettext system. If they are installed in a non-standard directory, you have to add it to your $PATH before calling ./configure.

Should I try to translate "Freeciv"?[]

No, just leave it "Freeciv" wherever you find it. (Also, note that the "c" in "Freeciv" is not capitalized.)

The Emacs po-mode doesn't start when I load a po-file. What should I do?[]

Make sure you have GNU Gettext installed. You can download it from a GNU ftp mirror site.

I have GNU Gettext installed but the po-mode still doesn't start. What should I do now?[]

Type 'info gettext' in a shell (or use the Emacs info-mode), select 'Basics' and select 'Installation'. Then you will find more information about installing the Emacs po-mode.

Emacs throws the error message "Fontifying XX.po...buffer too big" when I load a po-file. Is the po-file to big?[]

Don't worry. The buffer/file size is just fine. What Emacs is trying to say is that the value of the variable font-lock-maximum-size is too small. Emacs refuses to fontify buffers larger than this value because font-lock may consume a lot of resources for big buffers. To change the value, press 'M-x', type 'customize-variable', press Return, type 'font-lock-maximum-size' and press Return. Read the helptext in the buffer that opens and customize by changing the value to something like 524288 (2^19) (or whatever value you think is suitable). Now the files should become fontified when you open them (unless they are larger than 512kB).