Translating Qt Applications
-
Upload
qt-project -
Category
Technology
-
view
8.297 -
download
0
description
Transcript of Translating Qt Applications
09/12/09
Translating Qt applicationsIt does not have to be boring ;-)
Who is Benjamin Poulain at Nokia?
2
• first support engineer
– Linux and Mac OS X
• now Webkit developer
• pet projects
– graphical tablet
– Cocoa support
What do I do after work?
• some hacking
– web applications
• lots of sport: running, cycling, climbing
I am not so good on a snowboard
Why do I work on translations?
• my family do not speak english
➡need for localized software
• work on
– tutorial in french
– translation of Qt Creator
– french community of Qt
What are we gonna do today?
• Why bother?
• Translating your application
• Tools for translators
• Going further
• Conclusion
What are we gonna do today?
• Why bother?
• Translating your application
• Tools for translators
• Going further
• Conclusion
Translations increase your user base
Everybody speaks English. right?
Do not understand English
Secondary
Native speaker
writing an application is difficult ➜ spread it
What are we gonna do today?
• Why bother?• Translating your application
– Simple application– UI– Source– Integrate the translation
• Tools for translators• Going further• Conclusion
Ugly Snake is a mini game in Qt
How do we translate the application?
1) write code ready for translation
2) extract strings
3) translate
4) compile strings
Internationalization workflow:
What are we gonna do today?
• Why bother?• Translating your application
– Simple application– UI– Source– Integrate the translation
• Tools for translators• Going further• Conclusion
The .ui files are the biggest part
• most strings are in the .ui
• this is what is seen by the user
• good news: work out of the box
- string extraction
- translation
What are we gonna do today?
• Why bother?• Translating your application
– Simple application– UI– Source– Integrate the translation
• Tools for translators• Going further• Conclusion
Translate the strings with tr()
• QObject::tr() translate a string:trayIcon.showMessage("new message", "you have too many mail");
• works great with QString::arg():
tr("%n user(s) online").arg(userCount);
QString::number(userCount) + "users online";
trayIcon.showMessage(tr("new message"), tr("you have too many mail"));
Provide some context for short strings
tr("The %1 is %2").arg(...);What are 1, 2?
Provide some context for short strings
3 ways to add context:
– luck
– context in tr():
– comment in code
tr("The %1 is %2").arg(...);What are 1, 2?
tr("The %1 is %2", "The <extension> is <state>").arg(...);
//: The <extension> is <state>tr("The %1 is %2").arg(...);
How to mark strings for translations?
• tr() returns QString
• QT_TR_NOOP marks for translation
• translated later with tr()
char *const EDITOR = QT_TR_NOOP("emacs");
void function() { (...) QString editor = tr(EDITOR); (...)}
example:
What are we gonna do today?
• Why bother?• Translating your application
– Simple application– UI– Source– Integrate the translation
• Tools for translators• Going further• Conclusion
Applications use a compiled version of the translation
• lrelease compiles .ts in .qm
• .qm is the binary format for release
• fast lookup
• not into the binary
A translator must be installed
• QTranslator
- translate the strings
- load the .qm file:
QTranslator uglySnakeTranslator;uglySnakeTranslator.load("uglysnake_" + QLocale::system().name(), QCoreApplication::applicationDirPath());app.installTranslator(&uglySnakeTranslator);
What are we gonna do today?
• Why bother?
• Translating your application
• Tools for translators
• Going further
• Conclusion
There are two kinds of tools for translators
• offline ➜ Qt Linguist
• online ➜ Pootle, ...
Presentation of Linguist
Linguist is great but need to be distributed
• support multiple languages (simultaneously)
• great integration with Qt
• integration with the UI files:
• errors are spoted imediately
• full context
but: need to be distributed
Presentation of Pootle
Pootle is great, but offer no integration
• no need to distribute
• easier for amateur
but: no integration (ui files!)
What are we gonna do today?
• Why bother?• Translating your application• Tools for translators• Going further
– “context”– tricky UI– change the language– pitfalls
• Conclusion
One word, multiple concepts
edit
édition
éditer
noun
verb
tr("edit", "verb");tr("edit", "noun");
• short text ➜ context
• also in designer
Comments does not disambiguate the strings
QString a = tr("edit", "N97");QString b = tr("edit", "N900");
• works:
• do not work//: N97QString a = tr("edit");
//: N900QString b = tr("edit");
• why?
Understanding context and disambiguation
QPushButton::tr("edit", "verb");
context
disambiguation
QCoreApplication::translate("QPushButton", "edit", "verb");
QTranslator::translate("QPushButton", "edit", "verb");
context source disambiguation ➜ result
QPushButton edit verb ➜ editer
QPushButton edit ➜
source
Comments does not disambiguate the strings
QString a = tr("edit", "N97");QString b = tr("edit", "N900");
• works:
• do not work://: N97QString a = tr("edit");
//: N900QString b = tr("edit");
• solution://: N97QString a = tr("edit", "phoneA");
//: N900QString b = tr("edit", "phoneB");
What are we gonna do today?
• Why bother?• Translating your application• Tools for translators• Going further
– “context”– tricky UI– change the language– pitfalls
• Conclusion
The translation should fit the widgets
• the layouts adapt the widgets
• problems:
- fixed size- phone screen
Some images need a translation
• localize icons, images, etc
• qresource support locale:
<qresource lang="fr"> <file>burnIcon.png</file></qresource>
What if you want multiple UI?
• cultural conventions
• phone screens
• right to left interface
✓ Solution: QUiLoader to load the UI
X difficult to maintain
X difficult to document
What are we gonna do today?
• Why bother?• Translating your application• Tools for translators• Going further
– “context”– tricky UI– change the language– pitfalls
• Conclusion
What if the language is changed after the start?
• examples:
- phone
- public terminal
- MS Windows applications
Everything needs a new translation
• LanguageChange event on ::installTranslator()
• QWidget::changeEvent() to catch the event
• UI responds to retranslateUI()
• manual update for the code
void SettingsPanel::changeEvent(QEvent *e){ if (e->type() == QEvent::LanguageChange) { ui->retranslateUi(this); updateSpeedDescription(); } QWidget::changeEvent(e);}
When to change the translators?
• LocaleChange event to the active window
➡ install event filter on QApplication
➡ change the translators
What are we gonna do today?
• Why bother?• Translating your application• Tools for translators• Going further
– “context”– tricky UI– change the language– pitfalls
• Conclusion
Translate on painting is not a good strategy
char languageList[] = { QT_TR_NOOP("english"), QT_TR_NOOP("german") };
if (language == "english”) { ...
void paintEvent(QEvent *) { QString toShow = tr(m_language); ...}
list sorted alphabetically:
✓ Solution: use classes for identity, not strings
The source might not be in Latin 1
• tr() uses Latin 1 by default
✓ Solution 1: use English for the source
✓ Solution 2:
- QTextCodec::setCodecForTr()
- CODECFORTR = UTF-8
tr("Qt est génial"); // might fail
Mac uses an ordered list of language
• Mac OS X
- ordered list of languages
• language selection:QTranslator uglySnakeTranslator;uglySnakeTranslator.load("uglysnake_" + QLocale::system().name(), QCoreApplication::applicationDirPath());app.installTranslator(&uglySnakeTranslator);
Not accurate
✓ Solution: iterate over the languages of core foundation
What are we gonna do today?
• Why bother?
• Translating your application
• Tools for translators
• Going further
• Conclusion
Qt makes translation easy
• Internationalization is important
• Qt already solves the problems
• Minimal changes are needed in the code
– tr() every string
– provide context for short strings
➡ think about it when you develop