Add runtime translation support

Add support for gettext-based runtime translations. Enabled with
configure switch --enable-translation (no autodetection). Note that no
translation files are installed yet.
This commit is contained in:
Uoti Urpala 2010-03-08 22:48:50 +02:00
parent b34a88e4f4
commit 81065d41b6
3 changed files with 92 additions and 2 deletions

21
configure vendored
View File

@ -216,6 +216,7 @@ Installation directories:
--mandir=DIR directory for installing man pages [PREFIX/share/man]
--confdir=DIR directory for installing configuration files
[PREFIX/etc/mplayer]
--localedir=DIR directory for locale tree [PREFIX/share/locale]
--libdir=DIR directory for object code libraries [PREFIX/lib]
--codecsdir=DIR directory for binary codecs [LIBDIR/codecs]
--win32codecsdir=DIR directory for Windows DLLs [LIBDIR/codecs]
@ -398,6 +399,7 @@ Audio output:
--disable-select disable using select() on the audio device [enable]
Language options:
--enable-translation enable support for translated output [disable]
--charset=charset convert the console messages to this character set
--language-doc=lang language to use for the documentation [en]
--language-man=lang language to use for the man pages [en]
@ -656,6 +658,7 @@ _largefiles=yes
#language=en
_shm=auto
_linux_devfs=no
_translation=no
_charset="UTF-8"
_dynamic_plugins=no
_crash_debug=no
@ -733,6 +736,9 @@ for ac_option do
--realcodecsdir=*)
_realcodecsdir=$(echo $ac_option | cut -d '=' -f 2)
;;
--localedir=*)
_localedir=$(echo $ac_option | cut -d '=' -f 2)
;;
--with-install=*)
_install=$(echo $ac_option | cut -d '=' -f 2 )
@ -843,6 +849,8 @@ for ac_option do
--disable-debug)
_debug=
;;
--enable-translation) _translation=yes ;;
--disable-translation) _translation=no ;;
--enable-runtime-cpudetection) _runtime_cpudetection=yes ;;
--disable-runtime-cpudetection) _runtime_cpudetection=no ;;
--enable-cross-compile) _cross_compile=yes ;;
@ -1265,6 +1273,7 @@ test -z "$_datadir" && _datadir="$_prefix/share/mplayer"
test -z "$_mandir" && _mandir="$_prefix/share/man"
test -z "$_confdir" && _confdir="$_prefix/etc/mplayer"
test -z "$_libdir" && _libdir="$_prefix/lib"
test -z "$_localedir" && _localedir="$_prefix/share/locale"
# Determine our OS name and CPU architecture
if test -z "$_target" ; then
@ -2825,6 +2834,14 @@ fi
echores "$_langinfo"
echocheck "translation support"
if test "$_translation" = yes; then
def_translation="#define CONFIG_TRANSLATION 1"
else
def_translation="#undef CONFIG_TRANSLATION"
fi
echores "$_translation"
echocheck "language"
# Set preferred languages, "all" uses English as main language.
test -z "$language" && language=$LINGUAS
@ -7840,6 +7857,7 @@ DATADIR = \$(DESTDIR)$_datadir
LIBDIR = \$(DESTDIR)$_libdir
MANDIR = \$(DESTDIR)$_mandir
CONFDIR = \$(DESTDIR)$_confdir
LOCALEDIR = \$(DESTDIR)$_localedir
AR = $_ar
AS = $_cc
@ -8137,6 +8155,9 @@ cat > $TMPH << EOF
#define MPLAYER_DATADIR "$_datadir"
#define MPLAYER_CONFDIR "$_confdir"
#define MPLAYER_LIBDIR "$_libdir"
#define MPLAYER_LOCALEDIR "$_localedir"
$def_translation
/* definitions needed by included libraries */
#define HAVE_INTTYPES_H 1

View File

@ -5,6 +5,11 @@
#include "config.h"
#ifdef CONFIG_TRANSLATION
#include <locale.h>
#include <libintl.h>
#endif
#ifdef CONFIG_ICONV
#include <iconv.h>
#include <errno.h>
@ -77,6 +82,14 @@ void mp_msg_init(void){
if (!mp_msg_charset)
mp_msg_charset = get_term_charset();
#endif
#ifdef CONFIG_TRANSLATION
textdomain("mplayer");
char *localedir = getenv("MPLAYER_LOCALEDIR");
if (localedir == NULL && strlen(MPLAYER_LOCALEDIR))
localedir = MPLAYER_LOCALEDIR;
bindtextdomain("mplayer", localedir);
bind_textdomain_codeset("mplayer", "UTF-8");
#endif
}
int mp_msg_test(int mod, int lev)
@ -224,8 +237,63 @@ void mp_msg(int mod, int lev, const char *format, ...)
va_end(va);
}
char *mp_gtext(const char *string)
{
#ifdef CONFIG_TRANSLATION
/* gettext expects the global locale to be set with
* setlocale(LC_ALL, ""). However doing that would suck for a
* couple of reasons (locale stuff is badly designed and sucks in
* general).
*
* First setting the locale, especially LC_CTYPE, changes the
* behavior of various C functions and we don't want that - we
* want isalpha() for example to always behave like in the C
* locale.
* Second, there is no way to enforce a sane character set. All
* strings inside MPlayer must always be in utf-8, not in the
* character set specified by the system locale which could be
* something different and completely insane. The locale system
* lacks any way to say "set LC_CTYPE to utf-8, ignoring the
* default system locale if it specifies something different". We
* could try to work around that flaw by leaving LC_CTYPE to the C
* locale and only setting LC_MESSAGES (which is the variable that
* must be set to tell gettext which language to translate
* to). However if we leave LC_MESSAGES set then things like
* strerror() may produce completely garbled output when they try
* to translate their results but then try to convert some
* translated non-ASCII text to the character set specified by
* LC_CTYPE which would still be in the C locale (this doesn't
* affect gettext itself because it supports specifying the
* character set directly with bind_textdomain_codeset()).
*
* So the only solution (at leat short of trying to work around
* things possibly producing non-utf-8 output) is to leave all the
* locale variables unset. Note that this means it's not possible
* to get translated output from any libraries we call if they
* only rely on the broken locale system to specify the language
* to use; this is the case with libc for example.
*
* The locale changing below is rather ugly, but hard to avoid.
* gettext doesn't support specifying the translation target
* directly, only through locale.
* The main actual problem this could cause is interference with
* other threads; that could be avoided with thread-specific
* locale changes, but such functionality is less standard and I
* think it's not worth adding pre-emptively unless someone sees
* an actual problem case.
*/
setlocale(LC_MESSAGES, "");
string = gettext(string);
setlocale(LC_MESSAGES, "C");
#endif
return string;
}
void mp_tmsg(int mod, int lev, const char *format, ...)
{
va_list va;
va_start(va, format);
mp_msg_va(mod, lev, mp_gtext(format), va);
va_end(va);
}

View File

@ -118,12 +118,12 @@ int mp_msg_test(int mod, int lev);
#include "config.h"
char *mp_gtext(const char *string);
#define mp_tmsg mp_msg
void mp_msg_va(int mod, int lev, const char *format, va_list va);
#ifdef __GNUC__
void mp_msg(int mod, int lev, const char *format, ... ) __attribute__ ((format (printf, 3, 4)));
void mp_tmsg(int mod, int lev, const char *format, ... ) __attribute__ ((format (printf, 3, 4)));
# ifdef MP_DEBUG
# define mp_dbg(mod,lev, args... ) mp_msg(mod, lev, ## args )
# else
@ -131,6 +131,7 @@ void mp_msg(int mod, int lev, const char *format, ... ) __attribute__ ((format (
# endif
#else // not GNU C
void mp_msg(int mod, int lev, const char *format, ... );
void mp_tmsg(int mod, int lev, const char *format, ...)
# ifdef MP_DEBUG
# define mp_dbg(mod,lev, ... ) mp_msg(mod, lev, __VA_ARGS__)
# else