[bt-devel] Changing GUI language at runtime

Eeli Kaikkonen eekaikko at mail.student.oulu.fi
Thu Apr 23 11:55:33 MST 2009


Jaak Ristioja wrote:
> Hello
> 
> A day or two ago I proposed a feature over IRC about changing the
> language of the BibleTime at runtime, e.g. via a menu or settings
> dialog. Basically this is a quite simple task. I have already a
> TranslationManager class ready for the SVN head which provides a fully
> operational QMenu which lists all available languages. Upon activating
> an item in that menu, all widgets should receive the
> QEvent::LanguageChange event via QWidget::changeEvent. For the runtime
> translation feature to work, the following changes need to be made for
> most UI classes:
> 
> 1) All tr() calls need to be removed from directly any
> constructors/methods that initialize widgets etc and need to be put in a
> separate method, e.g. retranslateInterface(). That means we need to have
> pointers to all widgets in that specific class that need to be
> translated at run-time. That includes widget texts, titles, tooltips,
> whatsThis texts etc. Putting translated strings of message boxes in that
> method could speed up some things, but probably isn't practical. Sample:
> 
> MyWidget::MyWidget(QWidget *parent = 0) {
>     initWidgets();
>     retranslateInterface();
> 
>     QMessageBox::information(
>         this, tr("Information"),
>         tr("MyWidget loaded successfully!")
>     );
> }
> 
> void MyWidget::initWidgets() {
>     _childWidget = new QLabel(this);
> }
> 
> void MyWidget::retranslateInterface() {
>     // Here all widgets and menus and such will be translated
>     _childWidget->setText(tr("Hello %1!").arg(_worldString));
> }
> 
> 
> 2) Every widget needs to implement changeEvent. Sample:
> 
> void MyWidget::changeEvent(QEvent *event) {
>     if (event->type() == QEvent::LanguageChange) {
>         retranslateInterface();
>     }
>     SuperClassWidget::changeEvent(event);
> }
> 
> 
> 
> To bind the TranslationManager to BibleTime, it will suffice to
> initialize TranslationManager in main() after everything necessary for
> the CBTConfig to work is initialized:
> 
>     TranslationManager tm;
> 
> and to put the language menu somewhere:
> 
>     _settingsMenu->addMenu(_languageMenu = new QMenu(_settingsMenu));
>     TranslationManager::getInstance()->setLanguageMenu(_languageMenu);
> 
> 
> I'd like to provide a patch, but as I currently don't have the time to
> explore and patch the BibleTime source code in such great extent, I will
> only attach the preliminary TranslationManager class files. Currently
> they are to be placed into src/util/.
> 
> What do you think?

The idea of changing the language is good. For example, some people may 
have installed an English OS but would like to use some applications 
with their native language. In Linux it's already possible by giving the 
LANG env variable: LANG=fi_FI ./bibletime. (This is how I test the 
Finnish interface.) But for most users a GUI would be better.

However, I think that changing it on-the-fly is too much. Most people 
would change it only once or twice. They can be given a message: "The 
user interface language is changed after you close and start BibleTime 
again." Then it's enough to initialize the Qt translation mechanism in 
startup (see QTranslator documentation).

We could change the Config dialog layout a bit. Maybe add a new page 
"Fonts" and put the Fonts section from Languages there alone. The 
Languages page would have the name of Bible Books and the UI language. 
As a nice side effect this would improve the Config dialog layout and 
give more space for widgets.

Could you do that?

--Eeli Kaikkonen



More information about the bt-devel mailing list