如何强制 QLocale::system 改变

Posted

技术标签:

【中文标题】如何强制 QLocale::system 改变【英文标题】:How to force QLocale::system to change 【发布时间】:2014-01-28 13:50:02 【问题描述】:

我需要经常测试我的应用程序翻译成非英语语言,而仅仅为了做这个简单的检查而改变整个操作系统语言是非常不舒服的。 例如,如何使用环境变量更改 Qt 检测到的系统语言? 或使用命令行参数。

我尝试更改LANGLANGUAGE环境变量,但没有效果。 但是,在 GNOME 下它有!

UPD:代码我正在使用此类代码来确定系统区域设置并加载适当的翻译:

QTranslator app_translator;
if (!app_translator.load ("app_" + QLocale::system ().name (), app_tr_dir))
    qWarning ("Can't load app translator file for locale %s from %s", qPrintable (QLocale::system ().name ()), app_tr_dir.toLocal8Bit().data());
else
    app.installTranslator (&app_translator);

附:我的操作系统是 Kubuntu 13.10,Qt 版本是 4.8。

【问题讨论】:

【参考方案1】:

您总是可以通过 QLocale::setDefault() 方法更改语言环境。这是一个项目的示例:

void Language::setCurrentLanguage(Language::Languages language)

    if (language == Language::Arabic) 
        QLocale l(QLocale::Arabic, QLocale::SaudiArabia);
        QLocale::setDefault(l);
        dynamic_cast<MangoApp*>(qApp)->setLayoutDirection(Qt::RightToLeft);
        dynamic_cast<MangoApp*>(qApp)->removeAllTranslator();
        dynamic_cast<MangoApp*>(qApp)->loadQtTranslator();
        dynamic_cast<MangoApp*>(qApp)->loadMangoTranslator();

     else 
        QLocale l(QLocale::English, QLocale::UnitedStates);
        QLocale::setDefault(l);
        dynamic_cast<MangoApp*>(qApp)->setLayoutDirection(Qt::LeftToRight);
        dynamic_cast<MangoApp*>(qApp)->removeAllTranslator();
    

【讨论】:

谢谢,但我想要别的东西 - 在运行时更改语言而无需编写特殊代码。使用例如环境变量。 Qt 有一种方法可以确定当前的系统语言。我只是想欺骗它:) 在我的 Windows 机器上,我添加了一个环境变量 LANG=ar_SA.UTF8,它适用于 Designer.exe。在 Linux 上,您可以尝试像这样运行应用程序:LANG=en_US.UTF8 app_name。另一种解决方案是添加您自己的命令行并在应用程序启动时对其进行解析。 即您的应用程序通过更改LANG env 变量成功更改了它的语言?我正在尝试更改它,但没有效果。如果是这样,看起来问题出在我的应用程序中;(【参考方案2】:

对于测试,您可以使用类似的东西(只是正确的主要功能):

int main(int argc, char **argv) 
    QApplication app(argc, argv);

    QLocale localeUsedToDeterminateTranslators = QLocale::system();
    Q_FOREACH(QString a, app.arguments()) 
        const static localeParam = "-locale:";
        if (a.startsWith(localeParam)) 
           localeUsedToDeterminateTranslators = QLocale(a.mid(sizeof(localeParam)-1));
           break;
        
    
    ... // your normal code

然后,当您运行应用程序时,您可以使用额外参数运行它:./yourAppName -locale:nl。请参阅documentation of QLocale 了解可能的值。


编辑:我找到了更好的方法,有一个method QLocale::setDefault,所以这应该会更好:
int main(int argc, char **argv) 
    QApplication app(argc, argv);

    Q_FOREACH(QString a, app.arguments()) 
        const static localeParam = "-locale:";
        if (a.startsWith(localeParam)) 
           QLocale::setDefault(QLocale(a.mid(sizeof(localeParam)-1)));
           break;
        
    
    ...
    QTranslator app_translator;
    if (!app_translator.load ("app_" + QLocale().name (), app_tr_dir))
         qWarning ("Can't load app translator file for locale %s from %s", qPrintable (QLocale().name()), app_tr_dir.toLocal8Bit().data());
    else
         app.installTranslator (&app_translator);

【讨论】:

那么,您的建议只是使用自定义命令行参数?好的,这会有所帮助。但我只是好奇 - QLocale::system 如何确定当前选择的语言环境。理解这一点比通过蛮力创建适当的QLocale 对象更好:) 在代码中的某个地方,您应该使用语言环境来确定要加载哪些翻译。在您的代码中,您有 QLocale::system ().name (),因此您只需将其替换为 localeUsedToDeterminateTranslators.name() 在 Gnome 下 QLocale::system 理解 LANG 环境变量更改,所以看起来它是 KDE 错误/功能。谢谢,我会将您的回答标记为我的问题的解决方案。【参考方案3】:

使用LANGUAGE (not LANG) 环境变量肯定会更改QLocale::system().name() 返回的值,因为此环境变量优先于所有其他定义应用程序消息区域设置的方法(details)。

我在 Lubuntu 19.10 下使用 Qt 5.12 测试了它(意思是,使用 LXQt 桌面),它可以工作。命令是:

LANGUAGE=de ./application

如果这在 Kubuntu 下确实不起作用,则应将其报告为错误,因为 Kubuntu 会干扰应用程序被告知其语言环境的方式。

【讨论】:

以上是关于如何强制 QLocale::system 改变的主要内容,如果未能解决你的问题,请参考以下文章

如何强制excel单元格以指数方式改变颜色?

Jekyll:/folder 中的所有 HTML 文件,现在强制通过 /folder/page/ 呈现。如何改变?

强制布局发生以保证布局完成后宽度不会改变

sync---强制将被改变的内容立刻写入磁盘

如何实时改变音量

强制修改常量的值