Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4,095 changes: 4,095 additions & 0 deletions i18n/ru_RU.ts

Large diffs are not rendered by default.

3 changes: 2 additions & 1 deletion src/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,8 @@ qt6_add_translations(qdmr TS_FILES
${PROJECT_SOURCE_DIR}/i18n/de.ts ${PROJECT_SOURCE_DIR}/i18n/en_US.ts
${PROJECT_SOURCE_DIR}/i18n/sv.ts ${PROJECT_SOURCE_DIR}/i18n/it.ts
${PROJECT_SOURCE_DIR}/i18n/nl.ts ${PROJECT_SOURCE_DIR}/i18n/pl.ts
${PROJECT_SOURCE_DIR}/i18n/fr.ts ${PROJECT_SOURCE_DIR}/i18n/pt_BR.ts)
${PROJECT_SOURCE_DIR}/i18n/fr.ts ${PROJECT_SOURCE_DIR}/i18n/pt_BR.ts
${PROJECT_SOURCE_DIR}/i18n/ru_RU.ts)

#
# Icon generation
Expand Down
59 changes: 47 additions & 12 deletions src/application.cc
Original file line number Diff line number Diff line change
Expand Up @@ -45,10 +45,10 @@



inline QStringList getLanguages() {
static QStringList systemLocaleCandidates() {
QStringList languages = {QLocale::system().name()};
if (languages.last().contains("_")) {
languages.append(languages.last().split("_").first());
if (languages.last().contains(QLatin1Char('_'))) {
languages.append(languages.last().split(QLatin1Char('_')).first());
}
return languages;
}
Expand All @@ -75,17 +75,14 @@ Application::Application(int &argc, char *argv[])

// handle translations
_translator = new QTranslator(this);
foreach (QString language, getLanguages()) {
logDebug() << "Search for translation in ':/i18n/" << language << ".qm'.";
if (_translator->load(language, ":/i18n/", "", ".qm")) {
this->installTranslator(_translator);
logDebug() << "Installed translator for locale '" << QLocale::system().name() << "'.";
break;
}
Settings settings;
{
const QString langPref =
settings.uiLanguage().isEmpty() ? QStringLiteral("system") : settings.uiLanguage();
loadLanguage(langPref);
}

// load settings
Settings settings;
// load settings (same Settings instance as above)
// load databases
_repeater = new RepeaterDatabase(this);
if (settings.repeaterBookSourceEnabled())
Expand Down Expand Up @@ -917,3 +914,41 @@ Application::onPaletteChanged(const QPalette &palette) {
}


bool
Application::loadLanguage(const QString &localeId) {
removeTranslator(_translator);
bool loaded = false;
const bool useSystemLocale =
localeId.isEmpty() || localeId == QStringLiteral("system");

if (! useSystemLocale) {
logDebug() << "Try translation ':/i18n/" << localeId << ".qm'.";
loaded = _translator->load(localeId, QStringLiteral(":/i18n/"), QString(), QStringLiteral(".qm"));
if (! loaded && localeId.contains(QLatin1Char('_'))) {
const QString shortTag = localeId.split(QLatin1Char('_')).first();
loaded = _translator->load(shortTag, QStringLiteral(":/i18n/"), QString(), QStringLiteral(".qm"));
}
} else {
foreach (const QString &cand, systemLocaleCandidates()) {
logDebug() << "Try system translation ':/i18n/" << cand << ".qm'.";
loaded = _translator->load(cand, QStringLiteral(":/i18n/"), QString(), QStringLiteral(".qm"));
if (loaded)
break;
}
}

if (! loaded) {
logDebug() << "Fallback to ':/i18n/en_US.qm'.";
loaded = _translator->load(QStringLiteral("en_US"), QStringLiteral(":/i18n/"), QString(),
QStringLiteral(".qm"));
}

if (loaded) {
installTranslator(_translator);
logDebug() << "Installed translator for UI language preference '" << localeId << "'.";
} else {
logError() << "Failed to load any translation.";
}

return loaded;
}
3 changes: 3 additions & 0 deletions src/application.hh
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,9 @@ private slots:

void onPaletteChanged(const QPalette &palette);

private:
bool loadLanguage(const QString &localeId);

protected:
Config *_config;
MainWindow *_mainWindow;
Expand Down
57 changes: 56 additions & 1 deletion src/mainwindow.cc
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#include "mainwindow.hh"
#include "ui_mainwindow.h"
#include <QActionGroup>
#include <QProgressBar>
#include <QCloseEvent>
#include <QMessageBox>
Expand All @@ -26,7 +27,7 @@


MainWindow::MainWindow(Config *config, QWidget *parent)
: QMainWindow(parent), ui(new Ui::MainWindow)
: QMainWindow(parent), ui(new Ui::MainWindow), _languageGroup(nullptr)
{
ui->setupUi(this);
Application *app = qobject_cast<Application*>(QApplication::instance());
Expand Down Expand Up @@ -102,6 +103,45 @@ MainWindow::MainWindow(Config *config, QWidget *parent)
connect(ui->actionUpload, SIGNAL(triggered()), app, SLOT(uploadCodeplug()));
connect(ui->actionWriteSatellites, SIGNAL(triggered()), app, SLOT(uploadSatellites()));

_languageGroup = new QActionGroup(this);
_languageGroup->setExclusive(true);
ui->menuLanguage->clear();
// Locale ids match basenames of i18n/*.ts shipped as :/i18n/*.qm
static const struct {
const char *id;
const char *label;
} kUiLanguages[] = {
{"system", QT_TR_NOOP("System default")},
{"de", QT_TR_NOOP("German")},
{"en_US", QT_TR_NOOP("English")},
{"fr", QT_TR_NOOP("French")},
{"it", QT_TR_NOOP("Italian")},
{"nl", QT_TR_NOOP("Dutch")},
{"pl", QT_TR_NOOP("Polish")},
{"pt_BR", QT_TR_NOOP("Portuguese (Brazil)")},
{"ru_RU", QT_TR_NOOP("Russian")},
{"sv", QT_TR_NOOP("Swedish")},
};
for (const auto &entry : kUiLanguages) {
const QString id = QString::fromLatin1(entry.id);
QAction *a = ui->menuLanguage->addAction(tr(entry.label));
a->setCheckable(true);
a->setData(id);
_languageGroup->addAction(a);
QObject::connect(a, &QAction::triggered, this, [this, id]() {
const QString before =
Settings().uiLanguage().isEmpty() ? QStringLiteral("system") : Settings().uiLanguage();
Settings().setUiLanguage(id);
updateLanguageMenuChecks();
if (before != id) {
QMessageBox::information(
this, tr("Language"),
tr("The language will be applied fully after you restart the application."));
}
});
}
updateLanguageMenuChecks();

// Wire-up "General Settings" view
_generalSettings = new GeneralSettingsView(config);
ui->tabs->addTab(_generalSettings, tr("Settings"));
Expand Down Expand Up @@ -139,6 +179,21 @@ MainWindow::MainWindow(Config *config, QWidget *parent)
}


void
MainWindow::updateLanguageMenuChecks() {
const QString sel =
Settings().uiLanguage().isEmpty() ? QStringLiteral("system") : Settings().uiLanguage();
for (QAction *a : _languageGroup->actions()) {
if (a->data().toString() == sel) {
a->setChecked(true);
return;
}
}
if (!_languageGroup->actions().isEmpty())
_languageGroup->actions().first()->setChecked(true);
}


void
MainWindow::closeEvent(QCloseEvent *event) {
if (qobject_cast<Application*>(Application::instance())->isModified()) {
Expand Down
5 changes: 5 additions & 0 deletions src/mainwindow.hh
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@

#include <QMainWindow>

class QActionGroup;

class Config;
class GeneralSettingsView;
class RadioIDListView;
Expand All @@ -24,7 +26,10 @@ protected:
void closeEvent(QCloseEvent *event);

private:
void updateLanguageMenuChecks();

Ui::MainWindow *ui;
QActionGroup *_languageGroup;
GeneralSettingsView *_generalSettings;
RadioIDListView *_radioIdTab;
RoamingZoneListView *_roamingZoneList;
Expand Down
6 changes: 6 additions & 0 deletions src/mainwindow.ui
Original file line number Diff line number Diff line change
Expand Up @@ -109,9 +109,15 @@
<addaction name="actionRefreshOrbitalElements"/>
<addaction name="actionEditSatellites"/>
</widget>
<widget class="QMenu" name="menuLanguage">
<property name="title">
<string>Language</string>
</property>
</widget>
<addaction name="menuFile"/>
<addaction name="menuDevice"/>
<addaction name="menuDatabases"/>
<addaction name="menuLanguage"/>
<addaction name="menuHelp"/>
</widget>
<widget class="QStatusBar" name="statusbar">
Expand Down
10 changes: 10 additions & 0 deletions src/settings.cc
Original file line number Diff line number Diff line change
Expand Up @@ -301,6 +301,16 @@ Settings::setShowDisclaimer(bool show) {
setValue("showDisclaimer", show);
}

QString
Settings::uiLanguage() const {
return value("uiLanguage", QStringLiteral("system")).toString();
}

void
Settings::setUiLanguage(const QString &localeId) {
setValue("uiLanguage", localeId);
}

ConfigMergeVisitor::ItemStrategy
Settings::configMergeItemStrategy() const {
return (ConfigMergeVisitor::ItemStrategy)value(
Expand Down
4 changes: 4 additions & 0 deletions src/settings.hh
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,10 @@ public:
bool showDisclaimer() const;
void setShowDisclaimer(bool show);

/// Application UI language: `"system"` or a locale tag matching `i18n/*.qm` (e.g. `en_US`, `de`, `ru_RU`).
QString uiLanguage() const;
void setUiLanguage(const QString &localeId);

ConfigMergeVisitor::ItemStrategy configMergeItemStrategy() const;
void setConfigMergeItemStrategy(ConfigMergeVisitor::ItemStrategy strategy);

Expand Down