Qt入門(12)——Qt國際化
應用的國際化就是使應用成為能被非本國的人使用的過程。
有的情況下,國際化很簡單,例如,使一個US應用可被Australian或者British使用者理解,工作可能少於幾個拼寫修正。但是使一個US應用可以被Japanese使用者使用,或者一個Korean應用可被German使用者使用,就會需要軟體不僅工作於不同語言下,還要使用不同的輸入技術、字元編碼和表達習慣。
對所有使用者可見的文字使用QString
既然QString內部就使用Unicode編碼,那麼使用常見的文字處理手段,就可以透徹地處理世界上的每種語言。同時,既然所有向使用者呈現文字的Qt函式都把QString作為引數,也就沒有了char*到QString的轉換的時間開銷。
在“程式設計師空間”(例如QObject的名稱和檔案格式文字)的字串不需要使用QString;傳統的char*或者QCString類就夠用了。
你不大可能注意到你在使用Unicode;QString和QChar就如同早期版本的傳統C中的粗糙的const char*和char。
對所有文字形式的文字使用tr()
無論你的程式在哪裡對將會呈現給使用者的文字使用了"quoted text",要確保它被QApplication::translate()函式處理過。其實做到這一點只需要使用QObject::tr()。例如,假設LoginWidget是QWidget的一個子類:
這就解決了你可能要寫的使用者可見的字串的99%。
如果這些quoted text不是在QObject子類的成員函式中,可以使用一個適當的類的tr()函式,或者直接使用QApplication::translate()函式:
如果你需要不在函式裡的可翻譯文字,有兩個巨集可以幫忙:QT_TR_NOOP()和QT_TRANSLATE_NOOP()。它們僅僅標示出文字,以便於被下面描述的lupdate工具提取。巨集擴充套件為只是文字(沒有上下文)。
QT_TR_NOOP()的例子:
如果你使用定義的巨集QT_NO_CAST_ASCII編譯你的軟體,從而關閉了從const char*到QString的自動轉換,你很可能會捕捉到你錯過的字串。更多資訊參見QString::fromLatin1()。關閉這個轉換會使程式設計有點兒麻煩。
如果你的原始碼語言使用Latin-1之外的字符集,你會發現QObject::trUtf8()比QObject::tr()更好用,因為tr()依賴於QApplication::defaultCodec(),這使它比QObject::trUtf8()更脆弱。
對於加速鍵值(Accelerator value)使用QKeySequence()
加速鍵值,例如Ctrl+Q或者Alt+F,也需要翻譯。 如果你的應用給“Quit”直接編碼(hardcode)為CTRL+Key_Q,翻譯者就不能過載它了。正確的習慣用法是
對簡單引數使用QString::arg()
對於國際化的文字,在字串中類似printf()風格的插入引數一般是不好的選擇,因為有時候有必要在翻譯時改變引數的順序。不管怎樣,QString::arg()函式為引數替換提供了一種簡單的途徑:
有的情況下,國際化很簡單,例如,使一個US應用可被Australian或者British使用者理解,工作可能少於幾個拼寫修正。但是使一個US應用可以被Japanese使用者使用,或者一個Korean應用可被German使用者使用,就會需要軟體不僅工作於不同語言下,還要使用不同的輸入技術、字元編碼和表達習慣。
對所有使用者可見的文字使用QString
既然QString內部就使用Unicode編碼,那麼使用常見的文字處理手段,就可以透徹地處理世界上的每種語言。同時,既然所有向使用者呈現文字的Qt函式都把QString作為引數,也就沒有了char*到QString的轉換的時間開銷。
在“程式設計師空間”(例如QObject的名稱和檔案格式文字)的字串不需要使用QString;傳統的char*或者QCString類就夠用了。
你不大可能注意到你在使用Unicode;QString和QChar就如同早期版本的傳統C中的粗糙的const char*和char。
對所有文字形式的文字使用tr()
無論你的程式在哪裡對將會呈現給使用者的文字使用了"quoted text",要確保它被QApplication::translate()函式處理過。其實做到這一點只需要使用QObject::tr()。例如,假設LoginWidget是QWidget的一個子類:
LoginWidget::LoginWidget()
{
QLabel *label = new QLabel( tr("Password:"), this );
...
}
這就解決了你可能要寫的使用者可見的字串的99%。
如果這些quoted text不是在QObject子類的成員函式中,可以使用一個適當的類的tr()函式,或者直接使用QApplication::translate()函式:
void some_global_function( LoginWidget *logwid )
{
QLabel *label = new QLabel(
LoginWidget::tr("Password:"), logwid );
}
void same_global_function( LoginWidget *logwid )
{
QLabel *label = new QLabel(
qApp->translate("LoginWidget", "Password:"),
logwid );
}
如果你需要不在函式裡的可翻譯文字,有兩個巨集可以幫忙:QT_TR_NOOP()和QT_TRANSLATE_NOOP()。它們僅僅標示出文字,以便於被下面描述的lupdate工具提取。巨集擴充套件為只是文字(沒有上下文)。
QT_TR_NOOP()的例子:
QString FriendlyConversation::greeting( int greet_type )
{
static const char* greeting_strings[] = {
QT_TR_NOOP( "Hello" ),
QT_TR_NOOP( "Goodbye" )
};
return tr( greeting_strings[greet_type] );
}
QT_TRANSLATE_NOOP()的例子:
static const char* greeting_strings[] = {
QT_TRANSLATE_NOOP( "FriendlyConversation", "Hello" ),
QT_TRANSLATE_NOOP( "FriendlyConversation", "Goodbye" )
};
QString FriendlyConversation::greeting( int greet_type )
{
return tr( greeting_strings[greet_type] );
}
QString global_greeting( int greet_type )
{
return qApp->translate( "FriendlyConversation",
greeting_strings[greet_type] );
}
如果你使用定義的巨集QT_NO_CAST_ASCII編譯你的軟體,從而關閉了從const char*到QString的自動轉換,你很可能會捕捉到你錯過的字串。更多資訊參見QString::fromLatin1()。關閉這個轉換會使程式設計有點兒麻煩。
如果你的原始碼語言使用Latin-1之外的字符集,你會發現QObject::trUtf8()比QObject::tr()更好用,因為tr()依賴於QApplication::defaultCodec(),這使它比QObject::trUtf8()更脆弱。
對於加速鍵值(Accelerator value)使用QKeySequence()
加速鍵值,例如Ctrl+Q或者Alt+F,也需要翻譯。 如果你的應用給“Quit”直接編碼(hardcode)為CTRL+Key_Q,翻譯者就不能過載它了。正確的習慣用法是
QPopupMenu *file = new QPopupMenu( this );
file->insertItem( tr("&Quit"), this, SLOT(quit()),
QKeySequence(tr("Ctrl+Q", "File|Quit")) );
對簡單引數使用QString::arg()
對於國際化的文字,在字串中類似printf()風格的插入引數一般是不好的選擇,因為有時候有必要在翻譯時改變引數的順序。不管怎樣,QString::arg()函式為引數替換提供了一種簡單的途徑:
void FileCopier::showProgress( int done, int total,
const QString& current_file )
{
label.setText( tr("%1 of %2 files copied.\nCopying: %3")
.arg(done)
.arg(total)
.arg(current_file) );
}
相關文章
- QT6 國際化QT
- Qt入門(11)——Qt外掛QT
- QT中文亂碼與國際化支援QT
- Qt入門(13)——Qt的呼叫退出QT
- Qt入門(20)——Qt模組簡介QT
- QT快速入門QT
- 配置CLion管理Qt專案國際化支援QT
- QT程式設計------VS2012配置QT環境,QT入門程式設計QT程式設計
- Qt Quick 如何入門?QTUI
- 一種國際化Qt應用程式的方法QT
- Qt入門(9)——Qt中的執行緒支援QT執行緒
- QT開發快速入門-教程1:搭建QT開發環境QT開發環境
- Qt快速入門系列教程目錄QT
- Qt入門(3)——訊號和槽QT
- Qt入門(10)——除錯技術QT除錯
- Qt入門(15)——使用視窗部件QT
- Qt入門(16)——組裝視窗部件QT
- Qt入門(19)——自定義視窗部件QT
- Windows下Qt 5.2 for Android開發入門WindowsQTAndroid
- Qt入門(8)——事件和事件過濾器QT事件過濾器
- 什麼是qt,QT Creator, QT SDK, QT DesignerQT
- QT從入門到入土(四)——多執行緒QT執行緒
- 《Qt 6.x從入門到精通》簡介QT
- 零基礎學Qt4程式設計:Qt4開發入門與提升QT程式設計
- 《Qt 5.12實戰》簡介QT
- Qt5.12配置OpenCV教程QTOpenCV
- Qt入門(17)——組裝複雜的控制元件QT控制元件
- 12_QT跨平臺執行之使用QT控制蜂鳴器QT
- qt 載入winPcap庫QTPCA
- qt呼叫js,js呼叫qtQTJS
- Qt:QT右鍵選單QT
- QT父子與QT物件deleteQT物件delete
- QtQT
- QT從入門到入土(三)——訊號和槽機制QT
- QT從入門到入土(三)——檔案的讀寫操作QT
- QT從入門到入土(八)——專案打包和釋出QT
- 單例模式入門講解C++和Qt5單例模式C++QT
- Qt入門(14)——父視窗部件和子視窗部件QT